formatting
This commit is contained in:
@@ -1,43 +1,42 @@
|
||||
from functools import partial
|
||||
|
||||
|
||||
class BeamlineSwissfel:
|
||||
def __init__(self,components=['slits'],name=None):
|
||||
|
||||
def __init__(self, components=["slits"], name=None):
|
||||
self.name = name
|
||||
for comp_type in components:
|
||||
self.__dict__[f'_{comp_type}'] = []
|
||||
self.__dict__[comp] = partial(self._print_component_status,comp_type)
|
||||
self.__dict__[f"_{comp_type}"] = []
|
||||
self.__dict__[comp] = partial(self._print_component_status, comp_type)
|
||||
|
||||
|
||||
def append_component(self,comp_type,item):
|
||||
def append_component(self, comp_type, item):
|
||||
self.__dict__[comp_type].append(item)
|
||||
|
||||
def _get_component_status(self,comp_type):
|
||||
def _get_component_status(self, comp_type):
|
||||
s = []
|
||||
for comp in self.__dict__[comp_type]:
|
||||
s.append(comp.__repr__())
|
||||
return s
|
||||
|
||||
def _print_component_status(self,comp_type,linker='\n'):
|
||||
def _print_component_status(self, comp_type, linker="\n"):
|
||||
s = self._get_component_status()
|
||||
print(linker.join(s))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class Slits:
|
||||
|
||||
def __init__(self, slits):
|
||||
self.slits = slits
|
||||
|
||||
def __repr__(self):
|
||||
o = []
|
||||
|
||||
|
||||
for s in self.slits:
|
||||
o.append(s.name)
|
||||
tr = s.__repr__()
|
||||
for line in tr.splitlines():
|
||||
o.append(' '+line)
|
||||
return '\n'.join(o)
|
||||
o.append(" " + line)
|
||||
return "\n".join(o)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,31 +1,33 @@
|
||||
from slic.devices.general.motor import Motor
|
||||
from epics import PV
|
||||
|
||||
|
||||
class table:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
### ADC optical table ###
|
||||
self.x1 = Motor(Id + ':MOTOR_X1')
|
||||
self.x2 = Motor(Id + ':MOTOR_X2')
|
||||
self.y1 = Motor(Id + ':MOTOR_Y1')
|
||||
self.y2 = Motor(Id + ':MOTOR_Y2')
|
||||
self.y3 = Motor(Id + ':MOTOR_Y3')
|
||||
self.z = Motor(Id + ':MOTOR_Z')
|
||||
self.x = Motor(Id + ':W_X')
|
||||
self.y = Motor(Id + ':W_Y')
|
||||
self.z = Motor(Id + ':W_Z')
|
||||
self.pitch = Motor(Id + ':W_RX')
|
||||
self.yaw = Motor(Id + ':W_RY')
|
||||
self.roll = Motor(Id + ':W_RZ')
|
||||
self.modeSP = PV(Id + ':MODE_SP')
|
||||
self.status = PV(Id + ':SS_STATUS')
|
||||
self.x1 = Motor(Id + ":MOTOR_X1")
|
||||
self.x2 = Motor(Id + ":MOTOR_X2")
|
||||
self.y1 = Motor(Id + ":MOTOR_Y1")
|
||||
self.y2 = Motor(Id + ":MOTOR_Y2")
|
||||
self.y3 = Motor(Id + ":MOTOR_Y3")
|
||||
self.z = Motor(Id + ":MOTOR_Z")
|
||||
self.x = Motor(Id + ":W_X")
|
||||
self.y = Motor(Id + ":W_Y")
|
||||
self.z = Motor(Id + ":W_Z")
|
||||
self.pitch = Motor(Id + ":W_RX")
|
||||
self.yaw = Motor(Id + ":W_RY")
|
||||
self.roll = Motor(Id + ":W_RZ")
|
||||
self.modeSP = PV(Id + ":MODE_SP")
|
||||
self.status = PV(Id + ":SS_STATUS")
|
||||
|
||||
def __str__(self):
|
||||
return "Prime Table position\nx: %s mm\ny: %s mm\nz: %s\npitch: %s mrad\nyaw: %s mrad\nmode SP: %s \nstatus: %s" \
|
||||
% (self.x.wm(),self.y.wm(),self.z.wm(),self.pitch.wm(),self.yaw.wm(),self.modeSP.get(as_string=True),self.status.get())
|
||||
return "Prime Table position\nx: %s mm\ny: %s mm\nz: %s\npitch: %s mrad\nyaw: %s mrad\nmode SP: %s \nstatus: %s" % (self.x.wm(), self.y.wm(), self.z.wm(), self.pitch.wm(), self.yaw.wm(), self.modeSP.get(as_string=True), self.status.get())
|
||||
|
||||
def __repr__(self):
|
||||
return "{'x': %s, 'y': %s,'z': %s,'pitch': %s, 'yaw': %s, 'mode set point': %s,'status': %s}" \
|
||||
% (self.x,self.y,self.z,self.pitch,self.yaw,self.modeSP.get(as_string=True),self.status.get())
|
||||
return "{'x': %s, 'y': %s,'z': %s,'pitch': %s, 'yaw': %s, 'mode set point': %s,'status': %s}" % (self.x, self.y, self.z, self.pitch, self.yaw, self.modeSP.get(as_string=True), self.status.get())
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -4,71 +4,74 @@ from ..general.smaract import SmarActRecord
|
||||
|
||||
|
||||
class Huber:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
### Huber sample stages ###
|
||||
self.x = Motor(Id + ':MOTOR_X1')
|
||||
self.y = Motor(Id + ':MOTOR_Y1')
|
||||
self.z = Motor(Id + ':MOTOR_Z1')
|
||||
self.x = Motor(Id + ":MOTOR_X1")
|
||||
self.y = Motor(Id + ":MOTOR_Y1")
|
||||
self.z = Motor(Id + ":MOTOR_Z1")
|
||||
|
||||
def __str__(self):
|
||||
return "Huber Sample Stage %s\nx: %s mm\ny: %s mm\nz: %s mm" \
|
||||
%(self.Id, self.x.wm(),self.y.wm(),self.z.wm())
|
||||
return "Huber Sample Stage %s\nx: %s mm\ny: %s mm\nz: %s mm" % (self.Id, self.x.wm(), self.y.wm(), self.z.wm())
|
||||
|
||||
def __repr__(self):
|
||||
return "{'X': %s, 'Y': %s, 'Z': %s}"%(self.x.wm(),self.y.wm(),self.z.wm())
|
||||
return "{'X': %s, 'Y': %s, 'Z': %s}" % (self.x.wm(), self.y.wm(), self.z.wm())
|
||||
|
||||
|
||||
class VonHamosBragg:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
### Owis linear stages ###
|
||||
self.cry1 = Motor(Id + ':CRY_1')
|
||||
self.cry2 = Motor(Id + ':CRY_2')
|
||||
self.cry1 = Motor(Id + ":CRY_1")
|
||||
self.cry2 = Motor(Id + ":CRY_2")
|
||||
|
||||
def __str__(self):
|
||||
return "von Hamos positions\nCrystal 1: %s mm\nCrystal 2: %s mm" \
|
||||
% (self.cry1.wm(),self.cry2.wm())
|
||||
return "von Hamos positions\nCrystal 1: %s mm\nCrystal 2: %s mm" % (self.cry1.wm(), self.cry2.wm())
|
||||
|
||||
def __repr__(self):
|
||||
return "{'Crystal 1': %s, 'Crystal 2': %s}" % (self.cry1.wm(),self.cry2.wm())
|
||||
return "{'Crystal 1': %s, 'Crystal 2': %s}" % (self.cry1.wm(), self.cry2.wm())
|
||||
|
||||
|
||||
class Table:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
### ADC optical table ###
|
||||
self.x1 = Motor(Id + ':MOTOR_X1')
|
||||
self.y1 = Motor(Id + ':MOTOR_Y1')
|
||||
self.y2 = Motor(Id + ':MOTOR_Y2')
|
||||
self.y3 = Motor(Id + ':MOTOR_Y3')
|
||||
self.z1 = Motor(Id + ':MOTOR_Z1')
|
||||
self.z2 = Motor(Id + ':MOTOR_Z2')
|
||||
self.x = Motor(Id + ':W_X')
|
||||
self.y = Motor(Id + ':W_Y')
|
||||
self.z = Motor(Id + ':W_Z')
|
||||
self.pitch = Motor(Id + ':W_RX')
|
||||
self.yaw = Motor(Id + ':W_RY')
|
||||
self.roll = Motor(Id + ':W_RZ')
|
||||
self.modeSP = PV(Id + ':MODE_SP')
|
||||
self.status = PV(Id + ':SS_STATUS')
|
||||
self.x1 = Motor(Id + ":MOTOR_X1")
|
||||
self.y1 = Motor(Id + ":MOTOR_Y1")
|
||||
self.y2 = Motor(Id + ":MOTOR_Y2")
|
||||
self.y3 = Motor(Id + ":MOTOR_Y3")
|
||||
self.z1 = Motor(Id + ":MOTOR_Z1")
|
||||
self.z2 = Motor(Id + ":MOTOR_Z2")
|
||||
self.x = Motor(Id + ":W_X")
|
||||
self.y = Motor(Id + ":W_Y")
|
||||
self.z = Motor(Id + ":W_Z")
|
||||
self.pitch = Motor(Id + ":W_RX")
|
||||
self.yaw = Motor(Id + ":W_RY")
|
||||
self.roll = Motor(Id + ":W_RZ")
|
||||
self.modeSP = PV(Id + ":MODE_SP")
|
||||
self.status = PV(Id + ":SS_STATUS")
|
||||
|
||||
def __str__(self):
|
||||
return "Prime Table position\nx: %s mm\ny: %s mm\nz: %s\npitch: %s mrad\nyaw: %s mrad\nmode SP: %s \nstatus: %s" \
|
||||
% (self.x.wm(),self.y.wm(),self.z.wm(),self.pitch.wm(),self.yaw.wm(),self.modeSP.get(as_string=True),self.status.get())
|
||||
return "Prime Table position\nx: %s mm\ny: %s mm\nz: %s\npitch: %s mrad\nyaw: %s mrad\nmode SP: %s \nstatus: %s" % (self.x.wm(), self.y.wm(), self.z.wm(), self.pitch.wm(), self.yaw.wm(), self.modeSP.get(as_string=True), self.status.get())
|
||||
|
||||
def __repr__(self):
|
||||
return "{'x': %s, 'y': %s,'z': %s,'pitch': %s, 'yaw': %s, 'mode set point': %s,'status': %s}" \
|
||||
% (self.x,self.y,self.z,self.pitch,self.yaw,self.modeSP.get(as_string=True),self.status.get())
|
||||
return "{'x': %s, 'y': %s,'z': %s,'pitch': %s, 'yaw': %s, 'mode set point': %s,'status': %s}" % (self.x, self.y, self.z, self.pitch, self.yaw, self.modeSP.get(as_string=True), self.status.get())
|
||||
|
||||
|
||||
class Microscope:
|
||||
|
||||
def __init__(self, Id, gonio=None, rotat=None, alias_namespace=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
### Microscope motors ###
|
||||
self.focus = Motor(Id + ':FOCUS')
|
||||
self.zoom = Motor(Id + ':ZOOM')
|
||||
self.focus = Motor(Id + ":FOCUS")
|
||||
self.zoom = Motor(Id + ":ZOOM")
|
||||
# self._smaractaxes = {
|
||||
# 'gonio': '_xmic_gon', # will become self.gonio
|
||||
# 'rot': '_xmic_rot'} # """ self.rot
|
||||
@@ -76,29 +79,30 @@ class Microscope:
|
||||
self.rot = SmarActRecord(rotat) #TODO: can this be None?
|
||||
|
||||
def __str__(self):
|
||||
return "Microscope positions\nfocus: %s\nzoom: %s\ngonio: %s\nrot: %s"\
|
||||
% (self.focus.wm(),self.zoom.wm(),self.gonio.wm(),self.rot.wm())
|
||||
return "Microscope positions\nfocus: %s\nzoom: %s\ngonio: %s\nrot: %s" % (self.focus.wm(), self.zoom.wm(), self.gonio.wm(), self.rot.wm())
|
||||
|
||||
def __repr__(self):
|
||||
return "{'Focus': %s, 'Zoom': %s, 'Gonio': %s, 'Rot': %s}"\
|
||||
% (self.focus.wm(),self.zoom.wm(),self.gonio.wm(),self.rot.wm())
|
||||
return "{'Focus': %s, 'Zoom': %s, 'Gonio': %s, 'Rot': %s}" % (self.focus.wm(), self.zoom.wm(), self.gonio.wm(), self.rot.wm())
|
||||
|
||||
|
||||
# prism (as a SmarAct-only stage) is defined purely in ../aliases/alvra.py
|
||||
|
||||
|
||||
class Vacuum:
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
# Vacuum PVs for Prime chamber
|
||||
self.spectrometerP = PV(Id + 'MFR125-600:PRESSURE')
|
||||
self.intermediateP = PV(Id + 'MCP125-510:PRESSURE')
|
||||
self.sampleP = PV(Id + 'MCP125-410:PRESSURE')
|
||||
self.pDiff = PV('SARES11-EVSP-010:DIFFERENT')
|
||||
self.regulationStatus = PV('SARES11-EVGA-STM010:ACTIV_MODE')
|
||||
self.spectrometerTurbo = PV(Id + 'PTM125-600:HZ')
|
||||
self.intermediateTurbo = PV(Id + 'PTM125-500:HZ')
|
||||
self.sampleTurbo = PV(Id + 'PTM125-400:HZ')
|
||||
self.KBvalve = PV(Id + 'VPG124-230:PLC_OPEN')
|
||||
self.spectrometerP = PV(Id + "MFR125-600:PRESSURE")
|
||||
self.intermediateP = PV(Id + "MCP125-510:PRESSURE")
|
||||
self.sampleP = PV(Id + "MCP125-410:PRESSURE")
|
||||
self.pDiff = PV("SARES11-EVSP-010:DIFFERENT")
|
||||
self.regulationStatus = PV("SARES11-EVGA-STM010:ACTIV_MODE")
|
||||
self.spectrometerTurbo = PV(Id + "PTM125-600:HZ")
|
||||
self.intermediateTurbo = PV(Id + "PTM125-500:HZ")
|
||||
self.sampleTurbo = PV(Id + "PTM125-400:HZ")
|
||||
self.KBvalve = PV(Id + "VPG124-230:PLC_OPEN")
|
||||
|
||||
def __str__(self):
|
||||
valve = self.KBvalve.get()
|
||||
@@ -114,20 +118,21 @@ class Vacuum:
|
||||
currSpecTurbo = self.spectrometerTurbo.get()
|
||||
currInterTurbo = self.intermediateTurbo.get()
|
||||
currSamTurbo = self.sampleTurbo.get()
|
||||
|
||||
s = '**Prime chamber vacuum status**\n\n'
|
||||
s += 'Regulation mode: %s\n'%regStatusStr
|
||||
s += '%s\n'%valveStr
|
||||
s += 'Spectrometer pressure: %.3g mbar\n'%currSpecP
|
||||
s += 'Spectrometer Turbo pump: %s Hz\n'%currSpecTurbo
|
||||
s += 'Intermediate pressure: %.3g mbar\n'%currInterP
|
||||
s += 'Intermediate Turbo pump: %s Hz\n'%currInterTurbo
|
||||
s += 'Sample pressure: %.3g mbar\n'%currSamP
|
||||
s += 'Sample Turbo pump: %s Hz\n'%currSamTurbo
|
||||
s += 'Intermediate/Sample pressure difference: %.3g mbar\n'%currPDiff
|
||||
|
||||
s = "**Prime chamber vacuum status**\n\n"
|
||||
s += "Regulation mode: %s\n" % regStatusStr
|
||||
s += "%s\n" % valveStr
|
||||
s += "Spectrometer pressure: %.3g mbar\n" % currSpecP
|
||||
s += "Spectrometer Turbo pump: %s Hz\n" % currSpecTurbo
|
||||
s += "Intermediate pressure: %.3g mbar\n" % currInterP
|
||||
s += "Intermediate Turbo pump: %s Hz\n" % currInterTurbo
|
||||
s += "Sample pressure: %.3g mbar\n" % currSamP
|
||||
s += "Sample Turbo pump: %s Hz\n" % currSamTurbo
|
||||
s += "Intermediate/Sample pressure difference: %.3g mbar\n" % currPDiff
|
||||
return s
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3,7 +3,7 @@ from ..general.detectors import CameraCA, CameraBS
|
||||
from slic.core.adjustable import PVAdjustable
|
||||
from slic.utils.eco_components.aliases import Alias, append_object_to_object
|
||||
|
||||
# from ..devices_general.epics_wrappers import EnumSelector
|
||||
#from ..devices_general.epics_wrappers import EnumSelector
|
||||
from epics import PV
|
||||
from slic.utils.eco_epics.utilities_epics import EnumWrapper
|
||||
|
||||
@@ -23,16 +23,9 @@ def addMotorToSelf(self, Id=None, name=None):
|
||||
|
||||
|
||||
class Sigma:
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
camera_pv=None,
|
||||
zoomstage_pvs={
|
||||
"set_value": "SARES20-OPSI:MOT_SP",
|
||||
"readback": "SEARES20-OPSI:MOT_RB",
|
||||
},
|
||||
bshost=None,
|
||||
bsport=None,
|
||||
name=None,
|
||||
self, camera_pv=None, zoomstage_pvs={"set_value": "SARES20-OPSI:MOT_SP", "readback": "SEARES20-OPSI:MOT_RB",}, bshost=None, bsport=None, name=None,
|
||||
):
|
||||
self.alias = Alias(name)
|
||||
|
||||
@@ -40,13 +33,7 @@ class Sigma:
|
||||
|
||||
append_object_to_object
|
||||
if zoomstage_pvs:
|
||||
append_object_to_object(
|
||||
self,
|
||||
PVAdjustable,
|
||||
zoomstage_pvs["set_value"],
|
||||
pvname_readback=zoomstage_pvs["readback"],
|
||||
name="zoom"
|
||||
)
|
||||
append_object_to_object(self, PVAdjustable, zoomstage_pvs["set_value"], pvname_readback=zoomstage_pvs["readback"], name="zoom")
|
||||
|
||||
try:
|
||||
self.cam = CameraCA(camera_pv)
|
||||
@@ -71,9 +58,8 @@ class Sigma:
|
||||
|
||||
|
||||
class Qioptiq:
|
||||
def __init__(
|
||||
self, camera_pv=None, zoomstage_pv=None, bshost=None, bsport=None, name=None
|
||||
):
|
||||
|
||||
def __init__(self, camera_pv=None, zoomstage_pv=None, bshost=None, bsport=None, name=None):
|
||||
self.alias = Alias(name)
|
||||
|
||||
self.name = name
|
||||
|
||||
@@ -14,9 +14,8 @@ def addMotorToSelf(self, name=None, Id=None):
|
||||
|
||||
|
||||
class GPS:
|
||||
def __init__(
|
||||
self, name=None, Id=None, configuration=["base"], alias_namespace=None
|
||||
):
|
||||
|
||||
def __init__(self, name=None, Id=None, configuration=["base"], alias_namespace=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
@@ -39,18 +38,18 @@ class GPS:
|
||||
|
||||
if "phi_hex" in self.configuration:
|
||||
### motors PI hexapod ###
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-X", pvname_readback="SARES20-HEX_PI:POSI-X", name='xhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Y", pvname_readback="SARES20-HEX_PI:POSI-Y", name='yhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Z", pvname_readback="SARES20-HEX_PI:POSI-Z", name='zhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-U", pvname_readback="SARES20-HEX_PI:POSI-U", name='uhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-V", pvname_readback="SARES20-HEX_PI:POSI-V", name='vhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-W", pvname_readback="SARES20-HEX_PI:POSI-W", name='whex')
|
||||
# self.hex_x = PV("SARES20-HEX_PI:POSI-X")
|
||||
# self.hex_y = PV("SARES20-HEX_PI:POSI-Y")
|
||||
# self.hex_z = PV("SARES20-HEX_PI:POSI-Z")
|
||||
# self.hex_u = PV("SARES20-HEX_PI:POSI-U")
|
||||
# self.hex_v = PV("SARES20-HEX_PI:POSI-V")
|
||||
# self.hex_w = PV("SARES20-HEX_PI:POSI-W")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-X", pvname_readback="SARES20-HEX_PI:POSI-X", name="xhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Y", pvname_readback="SARES20-HEX_PI:POSI-Y", name="yhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Z", pvname_readback="SARES20-HEX_PI:POSI-Z", name="zhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-U", pvname_readback="SARES20-HEX_PI:POSI-U", name="uhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-V", pvname_readback="SARES20-HEX_PI:POSI-V", name="vhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-W", pvname_readback="SARES20-HEX_PI:POSI-W", name="whex")
|
||||
#self.hex_x = PV("SARES20-HEX_PI:POSI-X")
|
||||
#self.hex_y = PV("SARES20-HEX_PI:POSI-Y")
|
||||
#self.hex_z = PV("SARES20-HEX_PI:POSI-Z")
|
||||
#self.hex_u = PV("SARES20-HEX_PI:POSI-U")
|
||||
#self.hex_v = PV("SARES20-HEX_PI:POSI-V")
|
||||
#self.hex_w = PV("SARES20-HEX_PI:POSI-W")
|
||||
|
||||
if "hlxz" in self.configuration:
|
||||
### motors heavy load goniometer ###
|
||||
@@ -64,7 +63,6 @@ class GPS:
|
||||
addMotorToSelf(self, Id=Id + ":MOT_TBL_RX", name="rxhl")
|
||||
addMotorToSelf(self, Id=Id + ":MOT_TBL_RZ", name="rzhl")
|
||||
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = "*****GPS motor positions******\n"
|
||||
|
||||
@@ -79,6 +77,7 @@ class GPS:
|
||||
|
||||
|
||||
class XRD:
|
||||
|
||||
def __init__(self, name=None, Id=None, configuration=["base"]):
|
||||
"""X-ray diffractometer platform in AiwssFEL Bernina.\
|
||||
<configuration> : list of elements mounted on
|
||||
@@ -133,23 +132,22 @@ class XRD:
|
||||
|
||||
if "phi_hex" in self.configuration:
|
||||
### motors PI hexapod ###
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-X", pvname_readback="SARES20-HEX_PI:POSI-X", name='xhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Y", pvname_readback="SARES20-HEX_PI:POSI-Y", name='yhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Z", pvname_readback="SARES20-HEX_PI:POSI-Z", name='zhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-U", pvname_readback="SARES20-HEX_PI:POSI-U", name='uhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-V", pvname_readback="SARES20-HEX_PI:POSI-V", name='vhex')
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-W", pvname_readback="SARES20-HEX_PI:POSI-W", name='whex')
|
||||
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-X", pvname_readback="SARES20-HEX_PI:POSI-X", name="xhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Y", pvname_readback="SARES20-HEX_PI:POSI-Y", name="yhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-Z", pvname_readback="SARES20-HEX_PI:POSI-Z", name="zhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-U", pvname_readback="SARES20-HEX_PI:POSI-U", name="uhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-V", pvname_readback="SARES20-HEX_PI:POSI-V", name="vhex")
|
||||
append_object_to_object(self, PVAdjustable, "SARES20-HEX_PI:SET-POSI-W", pvname_readback="SARES20-HEX_PI:POSI-W", name="whex")
|
||||
|
||||
if "kappa" in self.configuration:
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KRX", name='eta')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KAP", name='kappa')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KPH", name='phi')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTY", name='zkap')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTX", name='xkap')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTZ", name='ykap')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DRX", name='rxkap')
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DRZ", name='rykap')
|
||||
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KRX", name="eta")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KAP", name="kappa")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_KPH", name="phi")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTY", name="zkap")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTX", name="xkap")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DTZ", name="ykap")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DRX", name="rxkap")
|
||||
append_object_to_object(self, Motor, "SARES21-XRD:MOT_KAP_DRZ", name="rykap")
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = "*****XRD motor positions******\n"
|
||||
|
||||
@@ -1,35 +1,36 @@
|
||||
from ..devices_general.smaract import SmarActRecord
|
||||
from epics import PV
|
||||
|
||||
|
||||
class XTG:
|
||||
def __init__(self,Id,alias_namespace=None):
|
||||
|
||||
def __init__(self, Id, alias_namespace=None):
|
||||
self.Id = Id
|
||||
|
||||
|
||||
### sample smaract motors ###
|
||||
self.sx = SmarActRecord(Id+':TRX3')
|
||||
self.sy = SmarActRecord(Id+':TRY3')
|
||||
|
||||
self.sx = SmarActRecord(Id + ":TRX3")
|
||||
self.sy = SmarActRecord(Id + ":TRY3")
|
||||
|
||||
### grating 1 motors ###
|
||||
self.g1x = SmarActRecord(Id+':TRX1')
|
||||
self.g1y = SmarActRecord(Id+':TRY1')
|
||||
self.g1z = SmarActRecord(Id+':TRZ1')
|
||||
self.g1x = SmarActRecord(Id + ":TRX1")
|
||||
self.g1y = SmarActRecord(Id + ":TRY1")
|
||||
self.g1z = SmarActRecord(Id + ":TRZ1")
|
||||
### grating 2 motors ###
|
||||
self.g2x = SmarActRecord(Id+':TRX2')
|
||||
self.g2y = SmarActRecord(Id+':TRY2')
|
||||
self.g2z = SmarActRecord(Id+':TRZ2')
|
||||
self.g2x = SmarActRecord(Id + ":TRX2")
|
||||
self.g2y = SmarActRecord(Id + ":TRY2")
|
||||
self.g2z = SmarActRecord(Id + ":TRZ2")
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = '*****SmarAct motor positions******\n'
|
||||
ostr = "*****SmarAct motor positions******\n"
|
||||
|
||||
for tkey,item in self.__dict__.items():
|
||||
if hasattr(item,'get_current_value'):
|
||||
for tkey, item in self.__dict__.items():
|
||||
if hasattr(item, "get_current_value"):
|
||||
pos = item.get_current_value()
|
||||
ostr += ' ' + tkey.ljust(10) + ' : % 14g\n'%pos
|
||||
ostr += " " + tkey.ljust(10) + " : % 14g\n" % pos
|
||||
return ostr
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
return self.get_adjustable_positions_str()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3,14 +3,15 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class EXP:
|
||||
def __init__(self,Id,alias_namespace=None):
|
||||
|
||||
def __init__(self, Id, alias_namespace=None):
|
||||
self.Id = Id
|
||||
|
||||
### motors 1.5M JF Zaber ###
|
||||
#self.det_x = Motor(Id + ':MOT_TX')
|
||||
#self.det_y = Motor(Id + ':MOT_TY')
|
||||
self.zaber_x = Motor(Id + ':MOT_TZ')
|
||||
self.qioptiq_zoom = Motor(Id + ':MOT_QIOPT_Z')
|
||||
self.zaber_x = Motor(Id + ":MOT_TZ")
|
||||
self.qioptiq_zoom = Motor(Id + ":MOT_QIOPT_Z")
|
||||
|
||||
### motors crystal ###
|
||||
#self.c_focus = Motor(Id + ':MOT_VT80')
|
||||
@@ -20,8 +21,8 @@ class EXP:
|
||||
s = "**Detector and crystal positions**\n"
|
||||
motors = "zaber_x qioptiq_zoom".split()
|
||||
for motor in motors:
|
||||
s+= " - %s %.4f\n"%(motor, getattr(self, motor).wm())
|
||||
s+= "\n"
|
||||
s += " - %s %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n"
|
||||
|
||||
return s
|
||||
|
||||
|
||||
@@ -3,31 +3,32 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class GPS:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None):
|
||||
self.Id = Id
|
||||
|
||||
### motors heavy load gps table ###
|
||||
self.xhl = Motor(Id + ':MOT_TBL_TX')
|
||||
self.zhl = Motor(Id + ':MOT_TBL_TZ')
|
||||
self.yhl = Motor(Id + ':MOT_TBL_TY')
|
||||
self.th = Motor(Id + ':MOT_MY_RYTH')
|
||||
self.xhl = Motor(Id + ":MOT_TBL_TX")
|
||||
self.zhl = Motor(Id + ":MOT_TBL_TZ")
|
||||
self.yhl = Motor(Id + ":MOT_TBL_TY")
|
||||
self.th = Motor(Id + ":MOT_MY_RYTH")
|
||||
try:
|
||||
self.rxhl = Motor(Id + ':MOT_TBL_RX')
|
||||
self.rxhl = Motor(Id + ":MOT_TBL_RX")
|
||||
except:
|
||||
print ('GPS.pitch not found')
|
||||
print("GPS.pitch not found")
|
||||
pass
|
||||
try:
|
||||
self.ryhl = Motor(Id + ':MOT_TBL_RY')
|
||||
self.ryhl = Motor(Id + ":MOT_TBL_RY")
|
||||
except:
|
||||
print ('GPS.roll not found')
|
||||
print("GPS.roll not found")
|
||||
pass
|
||||
|
||||
### motors heavy load gonio base ###
|
||||
self.xmu = Motor(Id + ':MOT_HEX_TX')
|
||||
self.mu = Motor(Id + ':MOT_HEX_RX')
|
||||
self.tth = Motor(Id + ':MOT_NY_RY2TH')
|
||||
self.xbase = Motor(Id + ':MOT_TX')
|
||||
self.ybase = Motor(Id + ':MOT_TY')
|
||||
self.xmu = Motor(Id + ":MOT_HEX_TX")
|
||||
self.mu = Motor(Id + ":MOT_HEX_RX")
|
||||
self.tth = Motor(Id + ":MOT_NY_RY2TH")
|
||||
self.xbase = Motor(Id + ":MOT_TX")
|
||||
self.ybase = Motor(Id + ":MOT_TY")
|
||||
|
||||
self.hex_x = PV("SARES20-HEX_PI:POSI-X")
|
||||
self.hex_y = PV("SARES20-HEX_PI:POSI-Y")
|
||||
@@ -40,24 +41,24 @@ class GPS:
|
||||
s = "**Heavy Load**\n"
|
||||
motors = "xmu mu tth xbase ybase".split()
|
||||
for motor in motors:
|
||||
s+= " - %s %.4f\n"%(motor,getattr(self,motor).wm())
|
||||
s += " - %s %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
|
||||
s+= " - HLX %.4f\n"%(self.xhl.wm())
|
||||
s+= " - HLY %.4f\n"%(self.yhl.wm())
|
||||
s+= " - HLZ %.4f\n"%(self.zhl.wm())
|
||||
s+= " - HLTheta %.4f\n"%(self.th.wm())
|
||||
s+= "\n"
|
||||
s += " - HLX %.4f\n" % (self.xhl.wm())
|
||||
s += " - HLY %.4f\n" % (self.yhl.wm())
|
||||
s += " - HLZ %.4f\n" % (self.zhl.wm())
|
||||
s += " - HLTheta %.4f\n" % (self.th.wm())
|
||||
s += "\n"
|
||||
|
||||
s+= "**Gonio**\n"
|
||||
s += "**Gonio**\n"
|
||||
motors = "xmu mu tth xbase ybase".split()
|
||||
for motor in motors:
|
||||
s+= " - %s %.4f\n"%(motor,getattr(self,motor).wm())
|
||||
s+= "\n"
|
||||
s += " - %s %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n"
|
||||
|
||||
s+= "**Hexapod**\n"
|
||||
s += "**Hexapod**\n"
|
||||
motors = "x y z u v w".split()
|
||||
for motor in motors:
|
||||
s+= " - hex_%s %.4f\n"%(motor,getattr(self,"hex_"+motor).get())
|
||||
s += " - hex_%s %.4f\n" % (motor, getattr(self, "hex_" + motor).get())
|
||||
return s
|
||||
|
||||
|
||||
|
||||
@@ -3,32 +3,33 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class XRD:
|
||||
|
||||
def __init__(self, Id, alias_namespace=None):
|
||||
self.Id = Id
|
||||
|
||||
### motors heavy load table ###
|
||||
self.xhl = Motor(Id + ':MOT_TBL_TX')
|
||||
self.zhl = Motor(Id + ':MOT_TBL_TZ')
|
||||
self.yhl = Motor(Id + ':MOT_TBL_TY')
|
||||
self.th = Motor(Id + ':MOT_MY_RYTH')
|
||||
self.zaber_x = Motor('SARES20-EXP' + ':MOT_TZ')
|
||||
self.xhl = Motor(Id + ":MOT_TBL_TX")
|
||||
self.zhl = Motor(Id + ":MOT_TBL_TZ")
|
||||
self.yhl = Motor(Id + ":MOT_TBL_TY")
|
||||
self.th = Motor(Id + ":MOT_MY_RYTH")
|
||||
self.zaber_x = Motor("SARES20-EXP" + ":MOT_TZ")
|
||||
try:
|
||||
self.rxhl = Motor(Id + ':MOT_TBL_RX')
|
||||
self.rxhl = Motor(Id + ":MOT_TBL_RX")
|
||||
except:
|
||||
print ('GPS.pitch not found')
|
||||
print("GPS.pitch not found")
|
||||
pass
|
||||
try:
|
||||
self.ryhl = Motor(Id + ':MOT_TBL_RY')
|
||||
self.ryhl = Motor(Id + ":MOT_TBL_RY")
|
||||
except:
|
||||
print ('GPS.roll not found')
|
||||
print("GPS.roll not found")
|
||||
pass
|
||||
|
||||
### motors heavy load gonio base ###
|
||||
#self.xmu = Motor(Id + ':MOT_HEX_TX')
|
||||
#self.mu = Motor(Id + ':MOT_HEX_RX')
|
||||
self.gamma = Motor(Id + ':MOT_NY_RY2TH')
|
||||
self.xbase = Motor(Id + ':MOT_TX')
|
||||
self.ybase = Motor(Id + ':MOT_TY')
|
||||
self.gamma = Motor(Id + ":MOT_NY_RY2TH")
|
||||
self.xbase = Motor(Id + ":MOT_TX")
|
||||
self.ybase = Motor(Id + ":MOT_TY")
|
||||
|
||||
#self.hex_x = PV("SARES20-HEX_PI:POSI-X")
|
||||
#self.hex_y = PV("SARES20-HEX_PI:POSI-Y")
|
||||
@@ -38,24 +39,22 @@ class XRD:
|
||||
#self.hex_w = PV("SARES20-HEX_PI:POSI-W")
|
||||
|
||||
### motors XRD arm ###
|
||||
self.delta = Motor(Id + ':MOT_DT_RX2TH')
|
||||
self.det_z = Motor(Id + ':MOT_D_T')
|
||||
self.cam_z = Motor(Id + ':MOT_P_T')
|
||||
|
||||
|
||||
self.delta = Motor(Id + ":MOT_DT_RX2TH")
|
||||
self.det_z = Motor(Id + ":MOT_D_T")
|
||||
self.cam_z = Motor(Id + ":MOT_P_T")
|
||||
|
||||
def __repr__(self):
|
||||
|
||||
s= "**Table**\n"
|
||||
s = "**Table**\n"
|
||||
motors = "xhl yhl zhl zaber_x th".split()
|
||||
for motor in motors:
|
||||
s+= " - %s %.4f\n"%(motor,getattr(self,motor).wm())
|
||||
s+= "\n"
|
||||
s+= "**Gonio**\n"
|
||||
s += " - %s %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n"
|
||||
s += "**Gonio**\n"
|
||||
motors = " xbase ybase gamma delta det_z cam_z".split()
|
||||
for motor in motors:
|
||||
s+= " - %s %.4f\n"%(motor,getattr(self,motor).wm())
|
||||
s+= "\n"
|
||||
s += " - %s %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n"
|
||||
|
||||
#s+= "**Hexapod**\n"
|
||||
#motors = "x y z u v w".split()
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
|
||||
class Hexapod_PI:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.x, self.y, self.z = [
|
||||
@@ -13,3 +15,6 @@ class Hexapod_PI:
|
||||
ValueRdback(self.id + f":SET-PIVOT-{i}", self.id + f":PIVOT-R-{i}")
|
||||
for i in "RST"
|
||||
]
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -4,6 +4,7 @@ from ..aliases import Alias
|
||||
|
||||
|
||||
class XRD:
|
||||
|
||||
def __init__(self, name=None, Id=None, configuration=[]):
|
||||
"""X-ray diffractometer platform in AiwssFEL Bernina.\
|
||||
<configuration> : list of elements mounted on
|
||||
|
||||
@@ -8,13 +8,7 @@ from .convenience import SpecConvenience
|
||||
class AdjustableVirtual(SpecConvenience):
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
adjustables,
|
||||
foo_get_current_value,
|
||||
foo_set_target_value_current_value,
|
||||
reset_current_value_to=False,
|
||||
append_aliases=False,
|
||||
name=None,
|
||||
self, adjustables, foo_get_current_value, foo_set_target_value_current_value, reset_current_value_to=False, append_aliases=False, name=None,
|
||||
):
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
@@ -40,10 +34,7 @@ class AdjustableVirtual(SpecConvenience):
|
||||
vals = (vals,)
|
||||
|
||||
def changer():
|
||||
self._active_changers = [
|
||||
adj.set_target_value(val, hold=False)
|
||||
for val, adj in zip(vals, self._adjustables)
|
||||
]
|
||||
self._active_changers = [adj.set_target_value(val, hold=False) for val, adj in zip(vals, self._adjustables)]
|
||||
for tc in self._active_changers:
|
||||
tc.wait()
|
||||
|
||||
@@ -55,21 +46,16 @@ class AdjustableVirtual(SpecConvenience):
|
||||
return self._currentChange
|
||||
|
||||
def get_current_value(self):
|
||||
return self._foo_get_current_value(
|
||||
*[adj.get_current_value() for adj in self._adjustables]
|
||||
)
|
||||
return self._foo_get_current_value(*[adj.get_current_value() for adj in self._adjustables])
|
||||
|
||||
def set_current_value(self, value):
|
||||
if not self._set_current_value:
|
||||
raise NotImplementedError(
|
||||
"There is no value setting implemented for this virtual adjuster!"
|
||||
)
|
||||
raise NotImplementedError("There is no value setting implemented for this virtual adjuster!")
|
||||
else:
|
||||
vals = self._foo_set_target_value_current_value(value)
|
||||
for adj, val in zip(self._adjustables, vals):
|
||||
adj.set_current_value(val)
|
||||
|
||||
|
||||
#TODO: below from DefaultRepresentation
|
||||
|
||||
def _get_name(self):
|
||||
@@ -81,7 +67,7 @@ class AdjustableVirtual(SpecConvenience):
|
||||
return self.Id
|
||||
|
||||
def __repr__(self):
|
||||
s = datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')+': '
|
||||
s = datetime.datetime.now().strftime("%Y/%m/%d %H:%M:%S") + ": "
|
||||
s += f"{colorama.Style.BRIGHT}{self._get_name()}{colorama.Style.RESET_ALL} at {colorama.Style.BRIGHT}{self.get_current_value():g}{colorama.Style.RESET_ALL}"
|
||||
return s
|
||||
|
||||
|
||||
@@ -5,24 +5,26 @@ import time
|
||||
from slic.core.task import Task
|
||||
|
||||
_basefolder = "/sf/alvra/config/lasertiming"
|
||||
_posTypes = ['user','dial','raw']
|
||||
_posTypes = ["user", "dial", "raw"]
|
||||
|
||||
def timeToStr(value,n=12):
|
||||
|
||||
def timeToStr(value, n=12):
|
||||
fmt = "%%+.%df" % n
|
||||
value = fmt%value
|
||||
value = fmt % value
|
||||
#print(value)
|
||||
idx_point = value.find(".")
|
||||
ret_str = value[:idx_point] + " ."
|
||||
ngroups = (len(value)-idx_point)//3
|
||||
for n in range(ngroups):
|
||||
ret_str += " %s" % value[idx_point+1+3*n:idx_point+1+3*(n+1)]
|
||||
#print(idx_point+1+3*n,idx_point+1*3*(n-1),ret_str)
|
||||
ret_str = value[:idx_point] + " ."
|
||||
ngroups = (len(value) - idx_point) // 3
|
||||
for n in range(ngroups):
|
||||
ret_str += " %s" % value[idx_point + 1 + 3 * n : idx_point + 1 + 3 * (n + 1)]
|
||||
#print(idx_point+1+3*n,idx_point+1*3*(n-1),ret_str)
|
||||
return ret_str
|
||||
|
||||
|
||||
|
||||
class Storage(object):
|
||||
def __init__(self,pvname):
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
|
||||
def __init__(self, pvname):
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self.pvname = pvname
|
||||
self.last_read_time = -1
|
||||
|
||||
@@ -38,7 +40,7 @@ class Storage(object):
|
||||
lmod = self.last_modified_time
|
||||
if os.path.isfile(self._filename):
|
||||
# need to read again ?
|
||||
if self.last_read_time == -1 or lmod > self.last_read_time :
|
||||
if self.last_read_time == -1 or lmod > self.last_read_time:
|
||||
#print("actually reading")
|
||||
value = float(np.loadtxt(self._filename))
|
||||
self.last_read_time = lmod
|
||||
@@ -46,96 +48,101 @@ class Storage(object):
|
||||
else:
|
||||
value = self.last_read
|
||||
else:
|
||||
print("could not read",self._filename)
|
||||
print("could not read", self._filename)
|
||||
value = 0
|
||||
return value
|
||||
|
||||
def store(self,value):
|
||||
with open(self._filename,"w") as f:
|
||||
f.write("# %s\n"%time.asctime())
|
||||
f.write("%.15f"%value)
|
||||
|
||||
def store(self, value):
|
||||
with open(self._filename, "w") as f:
|
||||
f.write("# %s\n" % time.asctime())
|
||||
f.write("%.15f" % value)
|
||||
|
||||
|
||||
class Pockels_trigger(PV):
|
||||
|
||||
""" this class is needed to store the offset in files and read in s """
|
||||
def __init__(self,pv_basename):
|
||||
|
||||
def __init__(self, pv_basename):
|
||||
pvname = pv_basename + "-RB"
|
||||
PV.__init__(self,pvname)
|
||||
self._pv_setvalue = PV(pv_basename + "-SP")
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
self._storage = Storage(pvname)
|
||||
PV.__init__(self, pvname)
|
||||
self._pv_setvalue = PV(pv_basename + "-SP")
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self._storage = Storage(pvname)
|
||||
|
||||
@property
|
||||
def offset(self): return self._storage.value
|
||||
|
||||
def offset(self):
|
||||
return self._storage.value
|
||||
|
||||
def get_dial(self):
|
||||
return super().get()*1e-6
|
||||
return super().get() * 1e-6
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
return self.get_dial()-self.offset
|
||||
return self.get_dial() - self.offset
|
||||
|
||||
def store(self,value=None):
|
||||
if value == None: value = self.get_dial()
|
||||
self._storage.store( value )
|
||||
def store(self, value=None):
|
||||
if value == None:
|
||||
value = self.get_dial()
|
||||
self._storage.store(value)
|
||||
|
||||
def move(self,value):
|
||||
def move(self, value):
|
||||
dial = value + self.offset
|
||||
self._pv_setvalue.put(dial*1e6)
|
||||
self._pv_setvalue.put(dial * 1e6)
|
||||
|
||||
def set(self,value):
|
||||
newoffset = self.get_dial()-value
|
||||
def set(self, value):
|
||||
newoffset = self.get_dial() - value
|
||||
self.store(newoffset)
|
||||
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
dial = timeToStr( self.get_dial(),n=12 )
|
||||
user = timeToStr( self.get(),n=12 )
|
||||
return "Pockel Trigger PV: %s user , dial = %s, %s"%(self.pvname,user,dial)
|
||||
dial = timeToStr(self.get_dial(), n=12)
|
||||
user = timeToStr(self.get(), n=12)
|
||||
return "Pockel Trigger PV: %s user , dial = %s, %s" % (self.pvname, user, dial)
|
||||
|
||||
|
||||
class Phase_shifter(PV):
|
||||
""" this class is needed to store the offset in files and read in ps """
|
||||
def __init__(self,pv_basename="SLAAR01-TSPL-EPL"):
|
||||
pvname = pv_basename+":CURR_DELTA_T"
|
||||
PV.__init__(self,pvname)
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
self._pv_setvalue = PV(pv_basename + ":NEW_DELTA_T")
|
||||
self._pv_execute = PV(pv_basename + ":SET_NEW_PHASE.PROC")
|
||||
self._storage = Storage(pvname)
|
||||
""" this class is needed to store the offset in files and read in ps """
|
||||
|
||||
def __init__(self, pv_basename="SLAAR01-TSPL-EPL"):
|
||||
pvname = pv_basename + ":CURR_DELTA_T"
|
||||
PV.__init__(self, pvname)
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self._pv_setvalue = PV(pv_basename + ":NEW_DELTA_T")
|
||||
self._pv_execute = PV(pv_basename + ":SET_NEW_PHASE.PROC")
|
||||
self._storage = Storage(pvname)
|
||||
|
||||
@property
|
||||
def offset(self): return self._storage.value
|
||||
|
||||
|
||||
def get_dial(self):
|
||||
return super().get()*1e-12
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
return self.get_dial()-self.offset
|
||||
|
||||
def store(self,value=None):
|
||||
if value == None: value = self.get_dial()
|
||||
self._storage.store( value )
|
||||
|
||||
def move(self,value):
|
||||
dial = value + self.offset
|
||||
dial_ps = dial*1e12
|
||||
self._pv_setvalue.put(dial_ps)
|
||||
time.sleep(0.1)
|
||||
self._pv_execute.put(1)
|
||||
while( np.abs(self.get()-value) > 100e-15 ): time.sleep(0.2)
|
||||
def offset(self):
|
||||
return self._storage.value
|
||||
|
||||
def set(self,value):
|
||||
newoffset = self.get_dial()-value
|
||||
def get_dial(self):
|
||||
return super().get() * 1e-12
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
return self.get_dial() - self.offset
|
||||
|
||||
def store(self, value=None):
|
||||
if value == None:
|
||||
value = self.get_dial()
|
||||
self._storage.store(value)
|
||||
|
||||
def move(self, value):
|
||||
dial = value + self.offset
|
||||
dial_ps = dial * 1e12
|
||||
self._pv_setvalue.put(dial_ps)
|
||||
time.sleep(0.1)
|
||||
self._pv_execute.put(1)
|
||||
while np.abs(self.get() - value) > 100e-15:
|
||||
time.sleep(0.2)
|
||||
|
||||
def set(self, value):
|
||||
newoffset = self.get_dial() - value
|
||||
self.store(newoffset)
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
dial = timeToStr( self.get_dial(),n=15 )
|
||||
user = timeToStr( self.get(),n=15 )
|
||||
return "Phase Shifter: user,dial = %s , %s"%(user,dial)
|
||||
dial = timeToStr(self.get_dial(), n=15)
|
||||
user = timeToStr(self.get(), n=15)
|
||||
return "Phase Shifter: user,dial = %s , %s" % (user, dial)
|
||||
|
||||
|
||||
#_pockels_in = Pockels_trigger("SLAAR-LTIM01-EVR0:Pul2-Delay")
|
||||
@@ -144,12 +151,13 @@ class Phase_shifter(PV):
|
||||
|
||||
|
||||
class PhaseShifterAramis:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self._pshifter = Phase_shifter(Id)
|
||||
self._elog = elog
|
||||
self.name = name
|
||||
|
||||
|
||||
def set_target_value(self, value, hold=False, check=True):
|
||||
""" Adjustable convention"""
|
||||
mover = lambda: self._pshifter.move(value)
|
||||
@@ -159,26 +167,24 @@ class PhaseShifterAramis:
|
||||
""" Adjustable convention"""
|
||||
pass
|
||||
|
||||
|
||||
def get_current_value(self,posType='user',readback=True):
|
||||
def get_current_value(self, posType="user", readback=True):
|
||||
""" Adjustable convention"""
|
||||
_keywordChecker([('posType',posType,_posTypes)])
|
||||
if posType == 'user':
|
||||
_keywordChecker([("posType", posType, _posTypes)])
|
||||
if posType == "user":
|
||||
return self._pshifter.get()
|
||||
if posType == 'dial':
|
||||
if posType == "dial":
|
||||
return self._pshifter.get_dial()
|
||||
|
||||
def set_current_value(self,value,posType='user'):
|
||||
def set_current_value(self, value, posType="user"):
|
||||
""" Adjustable convention"""
|
||||
_keywordChecker([('posType',posType,_posTypes)])
|
||||
if posType == 'user':
|
||||
_keywordChecker([("posType", posType, _posTypes)])
|
||||
if posType == "user":
|
||||
return self._motor.set(value)
|
||||
|
||||
|
||||
|
||||
def _keywordChecker(kw_key_list_tups):
|
||||
for tkw,tkey,tlist in kw_key_list_tups:
|
||||
assert tkey in tlist, "Keyword %s should be one of %s"%(tkw,tlist)
|
||||
for tkw, tkey, tlist in kw_key_list_tups:
|
||||
assert tkey in tlist, "Keyword %s should be one of %s" % (tkw, tlist)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -7,16 +7,15 @@ CONVERSION_FACTOR_METER_TO_MILLIMETER = 1e3
|
||||
CONVERSION_FACTOR_DELAY_TO_POS = SPEED_OF_LIGHT * CONVERSION_FACTOR_METER_TO_MILLIMETER / 2 # back and forth
|
||||
CONVERSION_FACTOR_POS_TO_DELAY = 1 / CONVERSION_FACTOR_DELAY_TO_POS
|
||||
|
||||
|
||||
def delay_to_pos(delay):
|
||||
return delay * CONVERSION_FACTOR_DELAY_TO_POS
|
||||
|
||||
|
||||
def pos_to_delay(pos):
|
||||
return pos * CONVERSION_FACTOR_POS_TO_DELAY
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class DelayStage:
|
||||
|
||||
def __init__(self, channel):
|
||||
@@ -27,21 +26,15 @@ class DelayStage:
|
||||
return "{} | {}".format(self.motor, self.delay)
|
||||
|
||||
def get(self):
|
||||
res = {
|
||||
"motor": self.motor.get_current_value(),
|
||||
"delay": self.delay.get_current_value()
|
||||
}
|
||||
res = {"motor": self.motor.get_current_value(), "delay": self.delay.get_current_value()}
|
||||
return res
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class Delay:
|
||||
|
||||
def __init__(self, stage):
|
||||
self._stage = stage
|
||||
self.delay_stage_offset =0.
|
||||
self.delay_stage_offset = 0.0
|
||||
self.name = self._stage.name
|
||||
self.Id = self._stage.Id
|
||||
self._elog = self._stage._elog
|
||||
@@ -67,11 +60,9 @@ class Delay:
|
||||
delay = pos_to_delay(value - self.delay_stage_offset)
|
||||
return self._stage.set_target_value(value, hold, check)
|
||||
|
||||
|
||||
def gui(self, guiType='xdm'):
|
||||
def gui(self, guiType="xdm"):
|
||||
return self._stage.gui()
|
||||
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self, value):
|
||||
self._stage._currentChange = self.set_target_value(value)
|
||||
@@ -89,18 +80,14 @@ class Delay:
|
||||
def stop(self):
|
||||
""" Adjustable convention"""
|
||||
try:
|
||||
self._stage._currentChange.stop()
|
||||
self._stage._currentChange.stop()
|
||||
except:
|
||||
self._stage.stop()
|
||||
pass
|
||||
|
||||
|
||||
self._stage.stop()
|
||||
|
||||
# return string with motor value as variable representation
|
||||
def __repr__(self):
|
||||
return "Delay at %s sec" % self.wm()
|
||||
|
||||
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
+111
-110
@@ -15,19 +15,22 @@ from slic.core.task import Task
|
||||
|
||||
try:
|
||||
import sys, os
|
||||
|
||||
tpath = os.path.dirname(__file__)
|
||||
sys.path.insert(0,os.path.join(tpath,'../../detector_integration_api'))
|
||||
sys.path.insert(0, os.path.join(tpath, "../../detector_integration_api"))
|
||||
#ask Leo(2018.03.14):
|
||||
#sys.path.insert(0,os.path.join(tpath,'../../jungfrau_utils'))
|
||||
#sys.path.insert(0,os.path.join(tpath,'../../jungfrau_utils'))
|
||||
from detector_integration_api import DetectorIntegrationClient
|
||||
except:
|
||||
print('NB: detector integration could not be imported!')
|
||||
print("NB: detector integration could not be imported!")
|
||||
|
||||
|
||||
_cameraArrayTypes = ['monochrome','rgb']
|
||||
_cameraArrayTypes = ["monochrome", "rgb"]
|
||||
|
||||
|
||||
class CameraCA:
|
||||
def __init__(self, pvname, cameraArrayType='monochrome',elog=None):
|
||||
|
||||
def __init__(self, pvname, cameraArrayType="monochrome", elog=None):
|
||||
self.Id = pvname
|
||||
self.isBS = False
|
||||
self.px_height = None
|
||||
@@ -36,41 +39,44 @@ class CameraCA:
|
||||
|
||||
def get_px_height(self):
|
||||
if not self.px_height:
|
||||
self.px_height = caget(self.Id + ':HEIGHT')
|
||||
self.px_height = caget(self.Id + ":HEIGHT")
|
||||
return int(self.px_height)
|
||||
|
||||
def get_px_width(self):
|
||||
if not self.px_width:
|
||||
self.px_width = caget(self.Id + ':WIDTH')
|
||||
self.px_width = caget(self.Id + ":WIDTH")
|
||||
return int(self.px_width)
|
||||
|
||||
def get_data(self):
|
||||
w = self.get_px_width()
|
||||
h = self.get_px_height()
|
||||
numpix = int(caget(self.Id+':FPICTURE.NORD'))
|
||||
i = caget(self.Id+':FPICTURE', count=numpix)
|
||||
return i.reshape(h,w)
|
||||
numpix = int(caget(self.Id + ":FPICTURE.NORD"))
|
||||
i = caget(self.Id + ":FPICTURE", count=numpix)
|
||||
return i.reshape(h, w)
|
||||
|
||||
def record_images(self,fina,N_images,sleeptime=0.2):
|
||||
with h5py.File(fina,'w') as f:
|
||||
def record_images(self, fina, N_images, sleeptime=0.2):
|
||||
with h5py.File(fina, "w") as f:
|
||||
d = []
|
||||
for n in range(N_images):
|
||||
d.append(self.get_data())
|
||||
sleep(sleeptime)
|
||||
f['images'] = np.asarray(d)
|
||||
f["images"] = np.asarray(d)
|
||||
|
||||
def gui(self, guiType='xdm'):
|
||||
def gui(self, guiType="xdm"):
|
||||
""" Adjustable convention"""
|
||||
cmd = ['caqtdm','-macro']
|
||||
cmd = ["caqtdm", "-macro"]
|
||||
|
||||
cmd.append('\"NAME=%s,CAMNAME=%s\"'%(self.Id, self.Id))
|
||||
cmd.append('/sf/controls/config/qt/Camera/CameraMiniView.ui')
|
||||
return subprocess.Popen(' '.join(cmd),shell=True)
|
||||
cmd.append('"NAME=%s,CAMNAME=%s"' % (self.Id, self.Id))
|
||||
cmd.append("/sf/controls/config/qt/Camera/CameraMiniView.ui")
|
||||
return subprocess.Popen(" ".join(cmd), shell=True)
|
||||
|
||||
|
||||
# /sf/controls/config/qt/Camera/CameraMiniView.ui" with macro "NAME=SAROP21-PPRM138,CAMNAME=SAROP21-PPRM138
|
||||
|
||||
#/sf/controls/config/qt/Camera/CameraMiniView.ui" with macro "NAME=SAROP21-PPRM138,CAMNAME=SAROP21-PPRM138
|
||||
|
||||
class CameraBS:
|
||||
def __init__(self,host=None,port=None,elog=None):
|
||||
|
||||
def __init__(self, host=None, port=None, elog=None):
|
||||
self._stream_host = host
|
||||
self._stream_port = port
|
||||
|
||||
@@ -79,40 +85,36 @@ class CameraBS:
|
||||
if self._instance_id not in client.get_server_info()["active_instances"]:
|
||||
raise ValueError("Requested pipeline is not running.")
|
||||
|
||||
def get_images(self,N_images):
|
||||
def get_images(self, N_images):
|
||||
data = []
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
input_stream.connect()
|
||||
|
||||
|
||||
for n in range(N_images):
|
||||
data.append(input_stream.receive().data.data['image'].value)
|
||||
data.append(input_stream.receive().data.data["image"].value)
|
||||
return data
|
||||
|
||||
def record_images(self,fina,N_images,dsetname='images'):
|
||||
def record_images(self, fina, N_images, dsetname="images"):
|
||||
ds = None
|
||||
with h5py.File(fina,'w') as f:
|
||||
with h5py.File(fina, "w") as f:
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
|
||||
input_stream.connect()
|
||||
|
||||
|
||||
for n in range(N_images):
|
||||
image = input_stream.receive().data.data['image'].value
|
||||
image = input_stream.receive().data.data["image"].value
|
||||
if not ds:
|
||||
ds = f.create_dataset(dsetname,dtype=image.dtype, shape=(N_images,)+image.shape)
|
||||
ds[n,:,:] = image
|
||||
ds = f.create_dataset(dsetname, dtype=image.dtype, shape=(N_images,) + image.shape)
|
||||
ds[n, :, :] = image
|
||||
|
||||
|
||||
class FeDigitizer:
|
||||
def __init__(self,Id,elog=None):
|
||||
|
||||
def __init__(self, Id, elog=None):
|
||||
self.Id = Id
|
||||
self.gain = EnumWrapper(Id+'-WD-gain')
|
||||
self._bias = PV(Id+'-HV_SET')
|
||||
self.channels = [
|
||||
Id+'-BG-DATA',
|
||||
Id+'-BG-DRS_TC',
|
||||
Id+'-BG-PULSEID-valid',
|
||||
Id+'-DATA',
|
||||
Id+'-DRS_TC',
|
||||
Id+'-PULSEID-valid']
|
||||
self.gain = EnumWrapper(Id + "-WD-gain")
|
||||
self._bias = PV(Id + "-HV_SET")
|
||||
self.channels = [Id + "-BG-DATA", Id + "-BG-DRS_TC", Id + "-BG-PULSEID-valid", Id + "-DATA", Id + "-DRS_TC", Id + "-PULSEID-valid"]
|
||||
|
||||
def set_bias(self, value):
|
||||
self._bias.put(value)
|
||||
@@ -120,20 +122,21 @@ class FeDigitizer:
|
||||
def get_bias(self):
|
||||
return self._bias.value
|
||||
|
||||
|
||||
class DiodeDigitizer:
|
||||
def __init__(self,Id,VME_crate=None,link=None,
|
||||
ch_0=7,ch_1=8, elog=None):
|
||||
|
||||
def __init__(self, Id, VME_crate=None, link=None, ch_0=7, ch_1=8, elog=None):
|
||||
self.Id = Id
|
||||
if VME_crate:
|
||||
self.diode_0 = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_0))
|
||||
self.diode_1 = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_1))
|
||||
|
||||
|
||||
self.diode_0 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_0))
|
||||
self.diode_1 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_1))
|
||||
|
||||
|
||||
class DIAClient:
|
||||
def __init__(self, Id, instrument=None, api_address = "http://sf-daq-2:10000", jf_name="JF_1.5M"):
|
||||
|
||||
def __init__(self, Id, instrument=None, api_address="http://sf-daq-2:10000", jf_name="JF_1.5M"):
|
||||
self.Id = Id
|
||||
self._api_address = api_address
|
||||
self._api_address = api_address
|
||||
self.client = DetectorIntegrationClient(api_address)
|
||||
print("\nDetector Integration API on %s" % api_address)
|
||||
# No pgroup by default
|
||||
@@ -147,36 +150,35 @@ class DIAClient:
|
||||
self.gain_file = "/sf/%s/config/jungfrau/gainMaps" % self.instrument
|
||||
self.update_config()
|
||||
|
||||
|
||||
def update_config(self, ):
|
||||
def update_config(self,):
|
||||
self.writer_config = {
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_data.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_data.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"n_frames": self.n_frames,
|
||||
"general/user": str(self.pgroup),
|
||||
"general/process": __name__,
|
||||
"general/created": str(datetime.now()),
|
||||
"general/instrument": self.instrument,
|
||||
# "general/correction": "test"
|
||||
#"general/correction": "test"
|
||||
}
|
||||
|
||||
self.backend_config = {
|
||||
"n_frames": self.n_frames,
|
||||
"bit_depth": 16,
|
||||
"gain_corrections_filename": self.gain_file, # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
#"gain_corrections_dataset": "gains",
|
||||
#"pede_corrections_filename": "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
#"pede_corrections_dataset": "gains",
|
||||
#"pede_mask_dataset": "pixel_mask",
|
||||
"n_frames": self.n_frames,
|
||||
"bit_depth": 16,
|
||||
"gain_corrections_filename": self.gain_file, # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
#"gain_corrections_dataset": "gains",
|
||||
#"pede_corrections_filename": "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
#"pede_corrections_dataset": "gains",
|
||||
#"pede_mask_dataset": "pixel_mask",
|
||||
#"activate_corrections_preview": True,
|
||||
# FIXME: HARDCODED!!!
|
||||
"is_HG0": False
|
||||
#FIXME: HARDCODED!!!
|
||||
"is_HG0": False,
|
||||
}
|
||||
|
||||
if self.pede_file != "":
|
||||
self.backend_config["gain_corrections_filename"] = self.gain_file # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
self.backend_config["gain_corrections_filename"] = self.gain_file # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
self.backend_config["gain_corrections_dataset"] = "gains"
|
||||
self.backend_config["pede_corrections_filename"] = self.pede_file # "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
self.backend_config["pede_corrections_filename"] = self.pede_file # "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
self.backend_config["pede_corrections_dataset"] = "gains"
|
||||
self.backend_config["pede_mask_dataset"] = "pixel_mask"
|
||||
self.backend_config["activate_corrections_preview"] = True
|
||||
@@ -189,22 +191,21 @@ class DIAClient:
|
||||
|
||||
self.detector_config = {
|
||||
"timing": "trigger",
|
||||
|
||||
# FIXME: HARDCODED
|
||||
"exptime": 0.000010,
|
||||
#FIXME: HARDCODED
|
||||
"exptime": 0.000010,
|
||||
"cycles": self.n_frames,
|
||||
#"delay" : 0.001992,
|
||||
"frames" : 1,
|
||||
"frames": 1,
|
||||
"dr": 16,
|
||||
}
|
||||
|
||||
|
||||
# Not needed anymore?
|
||||
#default_channels_list = parseChannelListFile(
|
||||
# '/sf/alvra/config/com/channel_lists/default_channel_list')
|
||||
|
||||
self.bsread_config = {
|
||||
'output_file': '/sf/%s/data/p%d/raw/test_bsread.h5' % (self.instrument, self.pgroup),
|
||||
'user_id': self.pgroup,
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_bsread.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"general/user": str(self.pgroup),
|
||||
"general/process": __name__,
|
||||
"general/created": str(datetime.now()),
|
||||
@@ -212,11 +213,11 @@ class DIAClient:
|
||||
#'Npulses':100,
|
||||
#'channels': default_channels_list
|
||||
}
|
||||
|
||||
# self.default_channels_list = jungfrau_utils.load_default_channel_list()
|
||||
|
||||
def reset(self):
|
||||
self.client.reset()
|
||||
#pass
|
||||
|
||||
def get_status(self):
|
||||
return self.client.get_status()
|
||||
@@ -229,18 +230,18 @@ class DIAClient:
|
||||
self.pgroup = pgroup
|
||||
self.update_config()
|
||||
|
||||
def set_bs_channels(self, ):
|
||||
def set_bs_channels(self,):
|
||||
print("Please update /sf/%s/config/com/channel_lists/default_channel_list and restart all services on the DAQ server" % self.instrument)
|
||||
|
||||
def set_config(self):
|
||||
self.reset()
|
||||
self.client.set_config({"writer": self.writer_config, "backend": self.backend_config, "detector": self.detector_config, "bsread": self.bsread_config})
|
||||
|
||||
def check_still_running(self, time_interval=.5):
|
||||
|
||||
def check_still_running(self, time_interval=0.5):
|
||||
cfg = self.get_config()
|
||||
running = True
|
||||
while running:
|
||||
if not self.get_status()['status'][-7:] == 'RUNNING':
|
||||
if not self.get_status()["status"][-7:] == "RUNNING":
|
||||
running = False
|
||||
break
|
||||
# elif not self.get_status()['status'][-20:]=='BSREAD_STILL_RUNNING':
|
||||
@@ -248,14 +249,15 @@ class DIAClient:
|
||||
# break
|
||||
else:
|
||||
sleep(time_interval)
|
||||
|
||||
|
||||
def take_pedestal(self, n_frames, analyze=True, n_bad_modules=0, update_config=True):
|
||||
from jungfrau_utils.scripts.jungfrau_run_pedestals import run as jungfrau_utils_run
|
||||
directory = '/sf/%s/data/p%d/raw/JF_pedestal/' % (self.instrument, self.pgroup)
|
||||
|
||||
directory = "/sf/%s/data/p%d/raw/JF_pedestal/" % (self.instrument, self.pgroup)
|
||||
if not os.path.exists(directory):
|
||||
print("Directory %s not existing, AND I CAN NOT CREATE IT, CALL DIMA" % directory)
|
||||
#os.makedirs(directory)
|
||||
|
||||
|
||||
res_dir = directory.replace("/raw/", "/res/")
|
||||
if not os.path.exists(res_dir):
|
||||
print("Directory %s not existing, creating it" % res_dir)
|
||||
@@ -263,49 +265,45 @@ class DIAClient:
|
||||
filename = "pedestal_%s" % datetime.now().strftime("%Y%m%d_%H%M")
|
||||
period = 0.04
|
||||
print("AAAAAAAAAAAAAAAAA", filename)
|
||||
jungfrau_utils_run(self._api_address, filename, directory, self.pgroup, period, self.detector_config["exptime"],
|
||||
n_frames, 1, analyze, n_bad_modules, self.instrument, self.jf_name)
|
||||
jungfrau_utils_run(self._api_address, filename, directory, self.pgroup, period, self.detector_config["exptime"], n_frames, 1, analyze, n_bad_modules, self.instrument, self.jf_name)
|
||||
|
||||
if update_config:
|
||||
self.pede_file = (directory + filename).replace("raw/", "res/").replace(".h5", ".res.h5")
|
||||
print("Pedestal file updated to %s" % self.pede_file)
|
||||
return self.pede_file
|
||||
|
||||
|
||||
def start(self):
|
||||
self.client.start()
|
||||
print("start acquisition")
|
||||
pass
|
||||
|
||||
def stop(self):
|
||||
self.client.stop()
|
||||
print("stop acquisition")
|
||||
pass
|
||||
print("stop acquisition")
|
||||
|
||||
def config_and_start_test(self):
|
||||
self.reset()
|
||||
self.set_config()
|
||||
self.start()
|
||||
pass
|
||||
|
||||
def wait_for_status(self,*args,**kwargs):
|
||||
return self.client.wait_for_status(*args,**kwargs)
|
||||
def wait_for_status(self, *args, **kwargs):
|
||||
return self.client.wait_for_status(*args, **kwargs)
|
||||
|
||||
def acquire(self, file_name=None, Npulses=100, JF_factor=1, bsread_padding=0):
|
||||
"""
|
||||
JF_factor?
|
||||
bsread_padding?
|
||||
"""
|
||||
file_rootdir = '/sf/%s/data/p%d/raw/' % (self.instrument, self.pgroup)
|
||||
|
||||
file_rootdir = "/sf/%s/data/p%d/raw/" % (self.instrument, self.pgroup)
|
||||
|
||||
if file_name is None:
|
||||
# FIXME /dev/null crashes the data taking (h5py can't close /dev/null and crashes)
|
||||
#FIXME /dev/null crashes the data taking (h5py can't close /dev/null and crashes)
|
||||
print("Not saving any data, as file_name is not set")
|
||||
file_name_JF = file_rootdir + "DelMe" + '_JF1p5M.h5'
|
||||
file_name_bsread = file_rootdir + "DelMe" + '.h5'
|
||||
file_name_JF = file_rootdir + "DelMe" + "_JF1p5M.h5"
|
||||
file_name_bsread = file_rootdir + "DelMe" + ".h5"
|
||||
else:
|
||||
# FIXME hardcoded
|
||||
file_name_JF = file_rootdir + file_name + '_JF1p5M.h5'
|
||||
file_name_bsread = file_rootdir + file_name + '.h5'
|
||||
#FIXME hardcoded
|
||||
file_name_JF = file_rootdir + file_name + "_JF1p5M.h5"
|
||||
file_name_bsread = file_rootdir + file_name + ".h5"
|
||||
|
||||
if self.pgroup == 0:
|
||||
raise ValueError("Please use set_pgroup() to set a pgroup value.")
|
||||
@@ -315,35 +313,38 @@ class DIAClient:
|
||||
self.update_config()
|
||||
#self.detector_config.update({
|
||||
# 'cycles': n_frames})
|
||||
self.writer_config.update({
|
||||
'output_file': file_name_JF,
|
||||
# 'n_messages': n_frames
|
||||
})
|
||||
self.writer_config.update(
|
||||
{
|
||||
"output_file": file_name_JF,
|
||||
#'n_messages': n_frames
|
||||
}
|
||||
)
|
||||
#self.backend_config.update({
|
||||
# 'n_frames': n_frames})
|
||||
self.bsread_config.update({
|
||||
'output_file':file_name_bsread,
|
||||
# 'Npulses': Npulses + bsread_padding
|
||||
})
|
||||
|
||||
self.bsread_config.update(
|
||||
{
|
||||
"output_file": file_name_bsread,
|
||||
#'Npulses': Npulses + bsread_padding
|
||||
}
|
||||
)
|
||||
|
||||
self.reset()
|
||||
self.set_config()
|
||||
#print(self.get_config())
|
||||
self.client.start()
|
||||
done = False
|
||||
|
||||
|
||||
while not done:
|
||||
stat = self.get_status()
|
||||
if stat['status'] =='IntegrationStatus.FINISHED':
|
||||
if stat["status"] == "IntegrationStatus.FINISHED":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.BSREAD_STILL_RUNNING':
|
||||
if stat["status"] == "IntegrationStatus.BSREAD_STILL_RUNNING":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.INITIALIZED':
|
||||
if stat["status"] == "IntegrationStatus.INITIALIZED":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.DETECTOR_STOPPED':
|
||||
if stat["status"] == "IntegrationStatus.DETECTOR_STOPPED":
|
||||
done = True
|
||||
sleep(.1)
|
||||
sleep(0.1)
|
||||
|
||||
return Task(acquire, hold=False)
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ from slic.utils.eco_epics.utilities_epics import EnumWrapper
|
||||
# from bsread import source, SUB
|
||||
import subprocess
|
||||
import h5py
|
||||
from time import sleep,time
|
||||
from time import sleep, time
|
||||
from datetime import datetime
|
||||
|
||||
from slic.core.task import Task
|
||||
@@ -16,75 +16,70 @@ from slic.utils.eco_components.aliases import Alias
|
||||
|
||||
|
||||
class PvDataStream:
|
||||
|
||||
def __init__(self, Id, name=None):
|
||||
self.Id = Id
|
||||
self._pv = PV(Id)
|
||||
self.name = name
|
||||
self.alias = Alias(self.name, channel=self.Id, channeltype="CA")
|
||||
|
||||
def collect(self,seconds=None,samples=None):
|
||||
def collect(self, seconds=None, samples=None):
|
||||
if (not seconds) and (not samples):
|
||||
raise Exception('Either a time interval or number of samples need to be defined.')
|
||||
raise Exception("Either a time interval or number of samples need to be defined.")
|
||||
try:
|
||||
self._pv.callbacks.pop(self._collection['ix_cb'])
|
||||
self._pv.callbacks.pop(self._collection["ix_cb"])
|
||||
except:
|
||||
pass
|
||||
self._collection = {'done':False}
|
||||
self._collection = {"done": False}
|
||||
self.data_collected = []
|
||||
if seconds:
|
||||
self._collection['start_time']= time()
|
||||
self._collection['seconds']= seconds
|
||||
stopcond = lambda: (time() - self._collection['start_time']) > self._collection['seconds']
|
||||
self._collection["start_time"] = time()
|
||||
self._collection["seconds"] = seconds
|
||||
stopcond = lambda: (time() - self._collection["start_time"]) > self._collection["seconds"]
|
||||
|
||||
def addData(**kw):
|
||||
if not stopcond():
|
||||
self.data_collected.append(kw['value'])
|
||||
self.data_collected.append(kw["value"])
|
||||
else:
|
||||
self._pv.callbacks.pop(self._collection['ix_cb'])
|
||||
self._collection['done'] = True
|
||||
elif samples:
|
||||
self._collection['samples'] = samples
|
||||
stopcond = lambda: len(self.data_collected) >= self._collection['samples']
|
||||
def addData(**kw):
|
||||
self.data_collected.append(kw['value'])
|
||||
if stopcond():
|
||||
self._pv.callbacks.pop(self._collection['ix_cb'])
|
||||
self._collection['done'] = True
|
||||
self._collection['ix_cb'] = self._pv.add_callback(addData)
|
||||
while not self._collection['done']:
|
||||
sleep(.005)
|
||||
return self.data_collected
|
||||
self._pv.callbacks.pop(self._collection["ix_cb"])
|
||||
self._collection["done"] = True
|
||||
|
||||
elif samples:
|
||||
self._collection["samples"] = samples
|
||||
stopcond = lambda: len(self.data_collected) >= self._collection["samples"]
|
||||
|
||||
def addData(**kw):
|
||||
self.data_collected.append(kw["value"])
|
||||
if stopcond():
|
||||
self._pv.callbacks.pop(self._collection["ix_cb"])
|
||||
self._collection["done"] = True
|
||||
|
||||
self._collection["ix_cb"] = self._pv.add_callback(addData)
|
||||
while not self._collection["done"]:
|
||||
sleep(0.005)
|
||||
return self.data_collected
|
||||
|
||||
def acquire(self, hold=False, **kwargs):
|
||||
_acquire = lambda: self.collect(**kwargs)
|
||||
return Task(_acquire, hold=hold)
|
||||
|
||||
def accumulate(self, n_buffer):
|
||||
if not hasattr(self,'_accumulate'):
|
||||
if not hasattr(self, "_accumulate"):
|
||||
self._accumulate = {"n_buffer": n_buffer, "ix": 0, "n_cb": -1}
|
||||
else:
|
||||
self._accumulate['n_buffer'] = n_buffer
|
||||
self._accumulate['ix'] = 0
|
||||
self._accumulate["n_buffer"] = n_buffer
|
||||
self._accumulate["ix"] = 0
|
||||
self._pv.callbacks.pop(self._accumulate["n_cb"], None)
|
||||
self._data = np.squeeze(np.zeros([n_buffer * 2, self._pv.count])) * np.nan
|
||||
|
||||
def addData(**kw):
|
||||
self._accumulate["ix"] = (self._accumulate["ix"] + 1) % self._accumulate[
|
||||
"n_buffer"
|
||||
]
|
||||
self._data[self._accumulate["ix"] :: self._accumulate["n_buffer"]] = kw[
|
||||
"value"
|
||||
]
|
||||
self._accumulate["ix"] = (self._accumulate["ix"] + 1) % self._accumulate["n_buffer"]
|
||||
self._data[self._accumulate["ix"] :: self._accumulate["n_buffer"]] = kw["value"]
|
||||
|
||||
self._accumulate["n_cb"] = self._pv.add_callback(addData)
|
||||
|
||||
def get_data(self):
|
||||
return self._data[
|
||||
self._accumulate["ix"]
|
||||
+ 1 : self._accumulate["ix"]
|
||||
+ 1
|
||||
+ self._accumulate["n_buffer"]
|
||||
]
|
||||
return self._data[self._accumulate["ix"] + 1 : self._accumulate["ix"] + 1 + self._accumulate["n_buffer"]]
|
||||
|
||||
data = property(get_data)
|
||||
|
||||
@@ -93,6 +88,7 @@ _cameraArrayTypes = ["monochrome", "rgb"]
|
||||
|
||||
|
||||
class CameraCA:
|
||||
|
||||
def __init__(self, pvname, cameraArrayType="monochrome", elog=None):
|
||||
self.Id = pvname
|
||||
self.isBS = False
|
||||
@@ -138,6 +134,7 @@ class CameraCA:
|
||||
|
||||
|
||||
class CameraBS:
|
||||
|
||||
def __init__(self, host=None, port=None, elog=None):
|
||||
self._stream_host = host
|
||||
self._stream_port = port
|
||||
@@ -149,9 +146,7 @@ class CameraBS:
|
||||
|
||||
def get_images(self, N_images):
|
||||
data = []
|
||||
with source(
|
||||
host=self._stream_host, port=self._stream_port, mode=SUB
|
||||
) as input_stream:
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
input_stream.connect()
|
||||
|
||||
for n in range(N_images):
|
||||
@@ -161,22 +156,19 @@ class CameraBS:
|
||||
def record_images(self, fina, N_images, dsetname="images"):
|
||||
ds = None
|
||||
with h5py.File(fina, "w") as f:
|
||||
with source(
|
||||
host=self._stream_host, port=self._stream_port, mode=SUB
|
||||
) as input_stream:
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
|
||||
input_stream.connect()
|
||||
|
||||
for n in range(N_images):
|
||||
image = input_stream.receive().data.data["image"].value
|
||||
if not ds:
|
||||
ds = f.create_dataset(
|
||||
dsetname, dtype=image.dtype, shape=(N_images,) + image.shape
|
||||
)
|
||||
ds = f.create_dataset(dsetname, dtype=image.dtype, shape=(N_images,) + image.shape)
|
||||
ds[n, :, :] = image
|
||||
|
||||
|
||||
class FeDigitizer:
|
||||
|
||||
def __init__(self, Id, elog=None):
|
||||
self.Id = Id
|
||||
self.gain = EnumWrapper(Id + "-WD-gain")
|
||||
@@ -198,8 +190,12 @@ class FeDigitizer:
|
||||
|
||||
|
||||
class DiodeDigitizer:
|
||||
|
||||
def __init__(self, Id, VME_crate=None, link=None, ch_0=7, ch_1=8, elog=None):
|
||||
self.Id = Id
|
||||
if VME_crate:
|
||||
self.diode_0 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_0))
|
||||
self.diode_1 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_1))
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -8,20 +8,20 @@ def addMotorToSelf(self, name=None, Id=None):
|
||||
self.alias.append(self.__dict__[name].alias)
|
||||
except:
|
||||
print(f"Warning! Could not find motor {name} (Id:{Id})")
|
||||
|
||||
|
||||
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
|
||||
|
||||
class stage:
|
||||
def __init__( self, name=None,vonHamos_horiz_pv=None,vonHamos_vert_pv = None ):
|
||||
|
||||
def __init__(self, name=None, vonHamos_horiz_pv=None, vonHamos_vert_pv=None):
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
addMotorToSelf(self, Id=vonHamos_horiz_pv, name="horiz")
|
||||
addMotorToSelf(self, Id=vonHamos_vert_pv, name="vert")
|
||||
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = "***** VonHamos motor positions******\n"
|
||||
|
||||
|
||||
@@ -11,81 +11,86 @@ from slic.core.task import Task
|
||||
# def _keywordChecker(kw_key_list_tups):
|
||||
# for tkw,tkey,tlist in kw_key_list_tups:
|
||||
# assert tkey in tlist, "Keyword %s should be one of %s"%(tkw,tlist)
|
||||
#
|
||||
#
|
||||
# class SmarActException(Exception):
|
||||
# """ raised to indicate a problem with a smartact"""
|
||||
#
|
||||
# def __init__(self, msg, *args):
|
||||
# Exception.__init__(self, *args)
|
||||
# self.msg = msg
|
||||
#
|
||||
# def __str__(self):
|
||||
# return str(self.msg)
|
||||
|
||||
# return str(self.msg)
|
||||
|
||||
# class SmarAct(Device):
|
||||
#
|
||||
# _extras = {'disabled':'_able.VAL', }
|
||||
# _init_list = ('VAL', 'DESC', 'RTYP')
|
||||
# _nonpvs = ('_prefix', '_pvs', '_delim', '_init', '_init_list', '_alias', '_extras')
|
||||
#
|
||||
# def __init__(self, name=None, timeout=3.0, record=None):
|
||||
# if name is None:
|
||||
# raise SmarActException("must supply SmarAct name")
|
||||
#
|
||||
#
|
||||
# if name.endswith('.VAL'):
|
||||
# name = name[:-4]
|
||||
# if name.endswith('.'):
|
||||
# name = name[:-1]
|
||||
#
|
||||
#
|
||||
# self._prefix = name
|
||||
# self._record = record
|
||||
# self._callbacks = {}
|
||||
#
|
||||
#
|
||||
# device.Device.__init__(self, name, delim='.',
|
||||
# attrs=self._init_list,
|
||||
# timeout=timeout)
|
||||
|
||||
|
||||
# for key, val in self._extras.items():
|
||||
# pvname = "%s%s" % (name, val)
|
||||
# self.add_pv(pvname, attr=key)
|
||||
|
||||
# self.put('disabled', 0)
|
||||
|
||||
# self.put('disabled', 0)
|
||||
|
||||
|
||||
class SmarActRecord:
|
||||
def __init__(self,Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self._drive = PV(Id+':DRIVE')
|
||||
self._rbv = PV(Id+':MOTRBV')
|
||||
self._hlm = PV(Id+':HLM')
|
||||
self._llm = PV(Id+':LLM')
|
||||
self._status = PV(Id+':STATUS')
|
||||
# self._set_pos = PV(Id+':SET_POS')
|
||||
self._stop = PV(Id+':STOP.PROC')
|
||||
# self._hold = PV(Id+':HOLD')
|
||||
self._twv = PV(Id+':TWV')
|
||||
self._elog = elog
|
||||
self.name = name
|
||||
# self.units = self._drive.get('EGU')
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self._drive = PV(Id + ":DRIVE")
|
||||
self._rbv = PV(Id + ":MOTRBV")
|
||||
self._hlm = PV(Id + ":HLM")
|
||||
self._llm = PV(Id + ":LLM")
|
||||
self._status = PV(Id + ":STATUS")
|
||||
# self._set_pos = PV(Id+':SET_POS')
|
||||
self._stop = PV(Id + ":STOP.PROC")
|
||||
# self._hold = PV(Id+':HOLD')
|
||||
self._twv = PV(Id + ":TWV")
|
||||
self._elog = elog
|
||||
self.name = name
|
||||
|
||||
# self.units = self._drive.get('EGU')
|
||||
|
||||
# Conventional methods and properties for all Adjustable objects
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold, stopper=self._stop.put(1))
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold, stopper=self._stop.put(1))
|
||||
|
||||
def stop(self):
|
||||
""" Adjustable convention"""
|
||||
self._stop.put(1)
|
||||
def stop(self):
|
||||
""" Adjustable convention"""
|
||||
self._stop.put(1)
|
||||
|
||||
def within_limits(self, val):
|
||||
""" returns whether a value for a motor is within drive limits"""
|
||||
return (val <= self._hlm.get('VAL') and val >= self._llm.get('VAL'))
|
||||
|
||||
def move_and_wait(self,value,checktime=.1):
|
||||
self._drive.put(value)
|
||||
while self._status.get() != 0:
|
||||
sleep(checktime)
|
||||
def within_limits(self, val):
|
||||
""" returns whether a value for a motor is within drive limits"""
|
||||
return val <= self._hlm.get("VAL") and val >= self._llm.get("VAL")
|
||||
|
||||
def move_and_wait(self, value, checktime=0.1):
|
||||
self._drive.put(value)
|
||||
while self._status.get() != 0:
|
||||
sleep(checktime)
|
||||
|
||||
# def move(self, val, relative=False, wait=False, timeout=300.0, ignore_limits=False, confirm_move=False):
|
||||
# """ moves smaract drive to position
|
||||
#
|
||||
#
|
||||
# arguments:
|
||||
# ==========
|
||||
# val value to move to (float) [Must be provided]
|
||||
@@ -94,7 +99,7 @@ class SmarActRecord:
|
||||
# ignore_limits try move without regard to limits (T/F) [F]
|
||||
# confirm_move try to confirm that move has begun (T/F) [F]
|
||||
# timeout max time for move to complete (in seconds) [300]
|
||||
#
|
||||
#
|
||||
# return values:
|
||||
# -13 : invalid value (cannot convert to float). Move not attempted.
|
||||
# -12 : target value outside soft limits. Move not attempted.
|
||||
@@ -106,10 +111,10 @@ class SmarActRecord:
|
||||
# -3 : move-with-wait finished, hard limit violation seen
|
||||
# 0 : move-with-wait finish OK.
|
||||
# 0 : move-without-wait executed, not cpmfirmed
|
||||
# 1 : move-without-wait executed, move confirmed
|
||||
# 1 : move-without-wait executed, move confirmed
|
||||
# 3 : move-without-wait finished, hard limit violation seen
|
||||
# 4 : move-without-wait finished, soft limit violation seen
|
||||
#
|
||||
#
|
||||
# """
|
||||
# NONFLOAT, OUTSIDE_LIMITS, UNCONNECTED = -13, -12, -11
|
||||
# TIMEOUT = -8
|
||||
@@ -120,22 +125,22 @@ class SmarActRecord:
|
||||
# val = float(val)
|
||||
# except TypeError:
|
||||
# return NONFLOAT
|
||||
#
|
||||
#
|
||||
# if relative:
|
||||
# val += self._drive.get('VAL')
|
||||
#
|
||||
#
|
||||
# # Check for limit violations
|
||||
# if not ignore_limits:
|
||||
# if not self.within_limits(val):
|
||||
# return OUTSIDE_LIMITS
|
||||
#
|
||||
#
|
||||
# stat = self._drive.put('VAL', val, wait=wait, timeout=timeout)
|
||||
# if stat is None:
|
||||
# return UNCONNECTED
|
||||
#
|
||||
#
|
||||
# if wait and stat == -1:
|
||||
# return TIMEOUT
|
||||
#
|
||||
#
|
||||
# if 1 == stat:
|
||||
# s0 = self._status.get('VAL')
|
||||
# s1 = s0
|
||||
@@ -173,10 +178,10 @@ class SmarActRecord:
|
||||
# return MOVE_BEGUN
|
||||
# return UNKNOWN_ERROR
|
||||
|
||||
def get_current_value(self):
|
||||
return self._rbv.get()
|
||||
def get_current_value(self):
|
||||
return self._rbv.get()
|
||||
|
||||
wm = get_current_value
|
||||
wm = get_current_value
|
||||
|
||||
# def set_current_value(self,value):
|
||||
# return self._drive.put(value)
|
||||
@@ -184,7 +189,7 @@ class SmarActRecord:
|
||||
# def get_precision(self):
|
||||
# """ Adjustable convention"""
|
||||
# pass
|
||||
#
|
||||
#
|
||||
# def set_precision(self):
|
||||
# """ Adjustable convention"""
|
||||
# pass
|
||||
@@ -200,10 +205,10 @@ class SmarActRecord:
|
||||
# def set_speedMax(self):
|
||||
# """ Adjustable convention"""
|
||||
# pass
|
||||
#
|
||||
#
|
||||
# def is_moving(self):
|
||||
# """ Adjustable convention"""
|
||||
# pass
|
||||
# pass
|
||||
|
||||
# def set_limits(self, values, posType='user', relative_to_present=False):
|
||||
# """ Adjustable convention"""
|
||||
@@ -220,28 +225,27 @@ class SmarActRecord:
|
||||
# def gui(self, guiType='xdm'):
|
||||
# """ Adjustable convention"""
|
||||
# cmd = ['caqtdm','-macro']
|
||||
#
|
||||
#
|
||||
# for i in range(len(self.Id)-1):
|
||||
# if self.Id[-i-1].isnumeric() is False:
|
||||
# M = self.Id[-i:]
|
||||
# P = self.Id[:-i]
|
||||
# print(P, M)
|
||||
# break
|
||||
#
|
||||
#
|
||||
# cmd.append('\"P=%s,M=%s\"'%(P, M))
|
||||
# # #cmd.append('/sf/common/config/qt/motorx_more.ui')
|
||||
# cmd.append('ESB_MX_SMARACT_mot_exp.ui')
|
||||
# # #os.system(' '.join(cmd))
|
||||
# return subprocess.Popen(' '.join(cmd),shell=True)
|
||||
#
|
||||
|
||||
#
|
||||
|
||||
# def mv(self,value):
|
||||
# self._currentChange = self.set_target_value(value)
|
||||
# def wm(self,*args,**kwargs):
|
||||
# return self.get_current_value(*args,**kwargs)
|
||||
# def mvr(self,value,*args,**kwargs):
|
||||
#
|
||||
#
|
||||
# if not self.is_moving():
|
||||
# startvalue = self.get_current_value(readback=True,*args,**kwargs)
|
||||
# else:
|
||||
@@ -250,27 +254,30 @@ class SmarActRecord:
|
||||
# def wait(self):
|
||||
# self._currentChange.wait()
|
||||
|
||||
|
||||
# return string with motor value as variable representation
|
||||
def __str__(self):
|
||||
return "SmarAct is at %s"%(self.get_current_value())
|
||||
# return string with motor value as variable representation
|
||||
def __str__(self):
|
||||
return "SmarAct is at %s" % (self.get_current_value())
|
||||
#return "SmarAct is at %s %s"%(self.wm(),self.units)
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
|
||||
# def __call__(self,value):
|
||||
# self._currentChange = self.set_target_value(value)
|
||||
#
|
||||
|
||||
|
||||
# class SmarActDevice(SmarActRecord):
|
||||
#
|
||||
# def __init__(self,Id,alias_namespace=None):
|
||||
# SmarActRecord.__init__(self, Id)
|
||||
# # self.Id = Id
|
||||
# #
|
||||
# # self.x = SmarActRecord(Id+':DRIVE')
|
||||
|
||||
|
||||
class SmarActStage:
|
||||
|
||||
def __init__(self, axes, name=None, z_undulator=None, description=None):
|
||||
self._keys = axes.keys()
|
||||
for axis in self._keys:
|
||||
@@ -278,12 +285,12 @@ class SmarActStage:
|
||||
ax = SmarActRecord(ax)
|
||||
self.__dict__[axis] = ax
|
||||
self.name = name
|
||||
|
||||
|
||||
def __str__(self):
|
||||
return "SmarAct positions\n%s" % "\n".join(["%s: %s"%(key,self.__dict__[key].wm()) for key in self._keys])
|
||||
|
||||
return "SmarAct positions\n%s" % "\n".join(["%s: %s" % (key, self.__dict__[key].wm()) for key in self._keys])
|
||||
|
||||
def __repr__(self):
|
||||
return str({key:self.__dict__[key].wm() for key in self._keys})
|
||||
return str({key: self.__dict__[key].wm() for key in self._keys})
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -22,6 +22,7 @@ def timeToStr(value, n=12):
|
||||
|
||||
|
||||
class Storage(object):
|
||||
|
||||
def __init__(self, pvname):
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self.pvname = pvname
|
||||
@@ -149,6 +150,7 @@ class Phase_shifter(PV):
|
||||
|
||||
|
||||
class PhaseShifterAramis:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self._pshifter = Phase_shifter(Id)
|
||||
@@ -180,7 +182,6 @@ class PhaseShifterAramis:
|
||||
return self._motor.set(value)
|
||||
|
||||
|
||||
|
||||
def _keywordChecker(kw_key_list_tups):
|
||||
for tkw, tkey, tlist in kw_key_list_tups:
|
||||
assert tkey in tlist, "Keyword %s should be one of %s" % (tkw, tlist)
|
||||
|
||||
@@ -23,19 +23,22 @@ import data_api as api
|
||||
|
||||
try:
|
||||
import sys, os
|
||||
|
||||
tpath = os.path.dirname(__file__)
|
||||
sys.path.insert(0,os.path.join(tpath,'../../detector_integration_api'))
|
||||
sys.path.insert(0, os.path.join(tpath, "../../detector_integration_api"))
|
||||
#ask Leo(2018.03.14):
|
||||
#sys.path.insert(0,os.path.join(tpath,'../../jungfrau_utils'))
|
||||
#sys.path.insert(0,os.path.join(tpath,'../../jungfrau_utils'))
|
||||
from detector_integration_api import DetectorIntegrationClient
|
||||
except:
|
||||
print('NB: detector integration could not be imported!')
|
||||
|
||||
print("NB: detector integration could not be imported!")
|
||||
|
||||
|
||||
_cameraArrayTypes = ["monochrome", "rgb"]
|
||||
|
||||
_cameraArrayTypes = ['monochrome','rgb']
|
||||
|
||||
class CameraCA:
|
||||
def __init__(self, pvname, cameraArrayType='monochrome',elog=None):
|
||||
|
||||
def __init__(self, pvname, cameraArrayType="monochrome", elog=None):
|
||||
self.Id = pvname
|
||||
self.isBS = False
|
||||
self.px_height = None
|
||||
@@ -44,41 +47,44 @@ class CameraCA:
|
||||
|
||||
def get_px_height(self):
|
||||
if not self.px_height:
|
||||
self.px_height = caget(self.Id + ':HEIGHT')
|
||||
self.px_height = caget(self.Id + ":HEIGHT")
|
||||
return self.px_height
|
||||
|
||||
def get_px_width(self):
|
||||
if not self.px_width:
|
||||
self.px_width = caget(self.Id + ':WIDTH')
|
||||
self.px_width = caget(self.Id + ":WIDTH")
|
||||
return self.px_width
|
||||
|
||||
def get_data(self):
|
||||
w = self.get_px_width()
|
||||
h = self.get_px_height()
|
||||
numpix = int(caget(self.Id+':FPICTURE.NORD'))
|
||||
i = caget(self.Id+':FPICTURE', count=numpix)
|
||||
return i.reshape(h,w)
|
||||
numpix = int(caget(self.Id + ":FPICTURE.NORD"))
|
||||
i = caget(self.Id + ":FPICTURE", count=numpix)
|
||||
return i.reshape(h, w)
|
||||
|
||||
def record_images(self,fina,N_images,sleeptime=0.2):
|
||||
with h5py.File(fina,'w') as f:
|
||||
def record_images(self, fina, N_images, sleeptime=0.2):
|
||||
with h5py.File(fina, "w") as f:
|
||||
d = []
|
||||
for n in range(N_images):
|
||||
d.append(self.get_data())
|
||||
sleep(sleeptime)
|
||||
f['images'] = np.asarray(d)
|
||||
f["images"] = np.asarray(d)
|
||||
|
||||
def gui(self, guiType='xdm'):
|
||||
def gui(self, guiType="xdm"):
|
||||
""" Adjustable convention"""
|
||||
cmd = ['caqtdm','-macro']
|
||||
cmd = ["caqtdm", "-macro"]
|
||||
|
||||
cmd.append('\"NAME=%s,CAMNAME=%s\"'%(self.Id, self.Id))
|
||||
cmd.append('/sf/controls/config/qt/Camera/CameraMiniView.ui')
|
||||
return subprocess.Popen(' '.join(cmd),shell=True)
|
||||
cmd.append('"NAME=%s,CAMNAME=%s"' % (self.Id, self.Id))
|
||||
cmd.append("/sf/controls/config/qt/Camera/CameraMiniView.ui")
|
||||
return subprocess.Popen(" ".join(cmd), shell=True)
|
||||
|
||||
|
||||
# /sf/controls/config/qt/Camera/CameraMiniView.ui" with macro "NAME=SAROP21-PPRM138,CAMNAME=SAROP21-PPRM138
|
||||
|
||||
#/sf/controls/config/qt/Camera/CameraMiniView.ui" with macro "NAME=SAROP21-PPRM138,CAMNAME=SAROP21-PPRM138
|
||||
|
||||
class CameraBS:
|
||||
def __init__(self,host=None,port=None,elog=None):
|
||||
|
||||
def __init__(self, host=None, port=None, elog=None):
|
||||
self._stream_host = host
|
||||
self._stream_port = port
|
||||
|
||||
@@ -87,40 +93,36 @@ class CameraBS:
|
||||
if self._instance_id not in client.get_server_info()["active_instances"]:
|
||||
raise ValueError("Requested pipeline is not running.")
|
||||
|
||||
def get_images(self,N_images):
|
||||
def get_images(self, N_images):
|
||||
data = []
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
input_stream.connect()
|
||||
|
||||
|
||||
for n in range(N_images):
|
||||
data.append(input_stream.receive().data.data['image'].value)
|
||||
data.append(input_stream.receive().data.data["image"].value)
|
||||
return data
|
||||
|
||||
def record_images(self,fina,N_images,dsetname='images'):
|
||||
def record_images(self, fina, N_images, dsetname="images"):
|
||||
ds = None
|
||||
with h5py.File(fina,'w') as f:
|
||||
with h5py.File(fina, "w") as f:
|
||||
with source(host=self._stream_host, port=self._stream_port, mode=SUB) as input_stream:
|
||||
|
||||
input_stream.connect()
|
||||
|
||||
|
||||
for n in range(N_images):
|
||||
image = input_stream.receive().data.data['image'].value
|
||||
image = input_stream.receive().data.data["image"].value
|
||||
if not ds:
|
||||
ds = f.create_dataset(dsetname,dtype=image.dtype, shape=(N_images,)+image.shape)
|
||||
ds[n,:,:] = image
|
||||
ds = f.create_dataset(dsetname, dtype=image.dtype, shape=(N_images,) + image.shape)
|
||||
ds[n, :, :] = image
|
||||
|
||||
|
||||
class FeDigitizer:
|
||||
def __init__(self,Id,elog=None):
|
||||
|
||||
def __init__(self, Id, elog=None):
|
||||
self.Id = Id
|
||||
self.gain = EnumWrapper(Id+'-WD-gain')
|
||||
self._bias = PV(Id+'-HV_SET')
|
||||
self.channels = [
|
||||
Id+'-BG-DATA',
|
||||
Id+'-BG-DRS_TC',
|
||||
Id+'-BG-PULSEID-valid',
|
||||
Id+'-DATA',
|
||||
Id+'-DRS_TC',
|
||||
Id+'-PULSEID-valid']
|
||||
self.gain = EnumWrapper(Id + "-WD-gain")
|
||||
self._bias = PV(Id + "-HV_SET")
|
||||
self.channels = [Id + "-BG-DATA", Id + "-BG-DRS_TC", Id + "-BG-PULSEID-valid", Id + "-DATA", Id + "-DRS_TC", Id + "-PULSEID-valid"]
|
||||
|
||||
def set_bias(self, value):
|
||||
self._bias.put(value)
|
||||
@@ -128,20 +130,21 @@ class FeDigitizer:
|
||||
def get_bias(self):
|
||||
return self._bias.value
|
||||
|
||||
|
||||
class DiodeDigitizer:
|
||||
def __init__(self,Id,VME_crate=None,link=None,
|
||||
ch_0=7,ch_1=8, elog=None):
|
||||
|
||||
def __init__(self, Id, VME_crate=None, link=None, ch_0=7, ch_1=8, elog=None):
|
||||
self.Id = Id
|
||||
if VME_crate:
|
||||
self.diode_0 = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_0))
|
||||
self.diode_1 = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_1))
|
||||
|
||||
|
||||
self.diode_0 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_0))
|
||||
self.diode_1 = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_1))
|
||||
|
||||
|
||||
class DIAClient:
|
||||
def __init__(self, Id, instrument=None, api_address = None, jf_name=None):
|
||||
|
||||
def __init__(self, Id, instrument=None, api_address=None, jf_name=None):
|
||||
self.Id = Id
|
||||
self._api_address = api_address
|
||||
self._api_address = api_address
|
||||
self.client = DetectorIntegrationClient(api_address)
|
||||
print("\nDetector Integration API on %s" % api_address)
|
||||
# No pgroup by default
|
||||
@@ -153,14 +156,14 @@ class DIAClient:
|
||||
self.instrument = instrument
|
||||
if instrument is None:
|
||||
print("ERROR: please configure the instrument parameter in DIAClient")
|
||||
self.gain_file = "/sf/%s/config/jungfrau/gainMaps" % self.instrument
|
||||
self.gain_file = "/sf/%s/config/jungfrau/gainMaps" % self.instrument
|
||||
self.update_config()
|
||||
self.active_clients = list(self.get_active_clients()['clients_enabled'].keys())
|
||||
self.active_clients = list(self.get_active_clients()["clients_enabled"].keys())
|
||||
|
||||
def update_config(self, ):
|
||||
def update_config(self,):
|
||||
self.writer_config = {
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_data.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_data.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"n_frames": self.n_frames,
|
||||
"general/user": str(self.pgroup),
|
||||
"general/process": __name__,
|
||||
@@ -172,22 +175,22 @@ class DIAClient:
|
||||
self.is_HG0 = True
|
||||
|
||||
self.backend_config = {
|
||||
"n_frames": self.n_frames,
|
||||
"bit_depth": 16,
|
||||
"gain_corrections_filename": self.gain_file, # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
#"gain_corrections_dataset": "gains",
|
||||
#"pede_corrections_filename": "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
#"pede_corrections_dataset": "gains",
|
||||
#"pede_mask_dataset": "pixel_mask",
|
||||
"n_frames": self.n_frames,
|
||||
"bit_depth": 16,
|
||||
"gain_corrections_filename": self.gain_file, # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
#"gain_corrections_dataset": "gains",
|
||||
#"pede_corrections_filename": "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
#"pede_corrections_dataset": "gains",
|
||||
#"pede_mask_dataset": "pixel_mask",
|
||||
#"activate_corrections_preview": True,
|
||||
# FIXME: HARDCODED!!!
|
||||
#FIXME: HARDCODED!!!
|
||||
"is_HG0": self.is_HG0
|
||||
}
|
||||
}
|
||||
|
||||
if self.pede_file != "":
|
||||
self.backend_config["gain_corrections_filename"] = self.gain_file # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
self.backend_config["gain_corrections_filename"] = self.gain_file # "/sf/alvra/config/jungfrau/jungfrau_4p5_gaincorrections_v0.h5",
|
||||
self.backend_config["gain_corrections_dataset"] = "gains"
|
||||
self.backend_config["pede_corrections_filename"] = self.pede_file # "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
self.backend_config["pede_corrections_filename"] = self.pede_file # "/sf/alvra/data/res/p%d/pedestal_20171210_1628_res.h5" % self.pgroup,
|
||||
self.backend_config["pede_corrections_dataset"] = "gains"
|
||||
self.backend_config["pede_mask_dataset"] = "pixel_mask"
|
||||
self.backend_config["activate_corrections_preview"] = True
|
||||
@@ -203,29 +206,25 @@ class DIAClient:
|
||||
# print(self.client.set_detector_value("setbit", "0x5d 0"))
|
||||
# else:
|
||||
# print(self.client.set_detector_value("clearbit", "0x5d 0"))
|
||||
|
||||
|
||||
self.detector_config = {
|
||||
"timing": "trigger",
|
||||
|
||||
|
||||
# "setbit" = "0x5d 0"
|
||||
|
||||
# FIXME: HARDCODED
|
||||
"exptime": 0.000005,
|
||||
#FIXME: HARDCODED
|
||||
"exptime": 0.000005,
|
||||
"cycles": self.n_frames,
|
||||
#"delay" : 0.001992,
|
||||
"frames" : 1,
|
||||
"frames": 1,
|
||||
"dr": 16,
|
||||
}
|
||||
|
||||
|
||||
# Not needed anymore?
|
||||
#default_channels_list = parseChannelListFile(
|
||||
# '/sf/alvra/config/com/channel_lists/default_channel_list')
|
||||
|
||||
self.bsread_config = {
|
||||
'output_file': '/sf/%s/data/p%d/raw/test_bsread.h5' % (self.instrument, self.pgroup),
|
||||
'user_id': self.pgroup,
|
||||
"output_file": "/sf/%s/data/p%d/raw/test_bsread.h5" % (self.instrument, self.pgroup),
|
||||
"user_id": self.pgroup,
|
||||
"general/user": str(self.pgroup),
|
||||
"general/process": __name__,
|
||||
"general/created": str(datetime.now()),
|
||||
@@ -233,11 +232,11 @@ class DIAClient:
|
||||
#'Npulses':100,
|
||||
#'channels': default_channels_list
|
||||
}
|
||||
|
||||
# self.default_channels_list = jungfrau_utils.load_default_channel_list()
|
||||
|
||||
def reset(self):
|
||||
self.client.reset()
|
||||
#pass
|
||||
|
||||
def get_status(self):
|
||||
return self.client.get_status()
|
||||
@@ -248,23 +247,23 @@ class DIAClient:
|
||||
|
||||
def get_active_clients(self):
|
||||
return self.client.get_clients_enabled()
|
||||
|
||||
|
||||
def set_pgroup(self, pgroup):
|
||||
self.pgroup = pgroup
|
||||
self.update_config()
|
||||
|
||||
def set_bs_channels(self, ):
|
||||
def set_bs_channels(self,):
|
||||
print("Please update /sf/%s/config/com/channel_lists/default_channel_list and restart all services on the DAQ server" % self.instrument)
|
||||
|
||||
def set_config(self):
|
||||
self.reset()
|
||||
self.client.set_config({"writer": self.writer_config, "backend": self.backend_config, "detector": self.detector_config, "bsread": self.bsread_config})
|
||||
|
||||
|
||||
def check_still_running(self, time_interval=1):
|
||||
cfg = self.get_config()
|
||||
running = True
|
||||
while running:
|
||||
if not self.get_status()['status'][-7:] == 'RUNNING':
|
||||
if not self.get_status()["status"][-7:] == "RUNNING":
|
||||
running = False
|
||||
break
|
||||
# elif not self.get_status()['status'][-20:]=='BSREAD_STILL_RUNNING':
|
||||
@@ -272,28 +271,28 @@ class DIAClient:
|
||||
# break
|
||||
else:
|
||||
sleep(time_interval)
|
||||
|
||||
|
||||
def take_pedestal(self, n_frames, analyze=True, n_bad_modules=0, update_config=True, period=0.04):
|
||||
from jungfrau_utils.scripts.jungfrau_run_pedestals import run as jungfrau_utils_run
|
||||
directory = '/sf/%s/data/p%d/raw/JF_pedestal/' % (self.instrument, self.pgroup)
|
||||
|
||||
directory = "/sf/%s/data/p%d/raw/JF_pedestal/" % (self.instrument, self.pgroup)
|
||||
if not os.path.exists(directory):
|
||||
print("Directory %s not existing, creating it" % directory)
|
||||
os.makedirs(directory)
|
||||
|
||||
|
||||
res_dir = directory.replace("/raw/", "/res/")
|
||||
if not os.path.exists(res_dir):
|
||||
print("Directory %s not existing, creating it" % res_dir)
|
||||
os.makedirs(res_dir)
|
||||
filename = "pedestal_%s.h5" % datetime.now().strftime("%Y%m%d_%H%M")
|
||||
# period = 0.02 # for 25 Hz this is 0.04, for 10 Hz this 0.1
|
||||
jungfrau_utils_run(self._api_address, filename, directory, self.pgroup, period, self.detector_config["exptime"],
|
||||
n_frames, 1, analyze, n_bad_modules, self.instrument, self.jf_name)
|
||||
jungfrau_utils_run(self._api_address, filename, directory, self.pgroup, period, self.detector_config["exptime"], n_frames, 1, analyze, n_bad_modules, self.instrument, self.jf_name)
|
||||
|
||||
if update_config:
|
||||
self.pede_file = (directory + filename).replace("raw/", "res/").replace(".h5", "_res.h5")
|
||||
print("Pedestal file updated to %s" % self.pede_file)
|
||||
return self.pede_file
|
||||
|
||||
|
||||
def start(self):
|
||||
self.client.start()
|
||||
print("start acquisition")
|
||||
@@ -301,7 +300,7 @@ class DIAClient:
|
||||
|
||||
def stop(self):
|
||||
self.client.stop()
|
||||
print("stop acquisition")
|
||||
print("stop acquisition")
|
||||
pass
|
||||
|
||||
def config_and_start_test(self):
|
||||
@@ -310,25 +309,25 @@ class DIAClient:
|
||||
self.start()
|
||||
pass
|
||||
|
||||
def wait_for_status(self,*args,**kwargs):
|
||||
return self.client.wait_for_status(*args,**kwargs)
|
||||
def wait_for_status(self, *args, **kwargs):
|
||||
return self.client.wait_for_status(*args, **kwargs)
|
||||
|
||||
def acquire(self, file_name=None, Npulses=100, JF_factor=1, bsread_padding=0, reset_before=False):
|
||||
"""
|
||||
JF_factor?
|
||||
bsread_padding?
|
||||
"""
|
||||
file_rootdir = '/sf/%s/data/p%d/raw/' % (self.instrument, self.pgroup)
|
||||
|
||||
file_rootdir = "/sf/%s/data/p%d/raw/" % (self.instrument, self.pgroup)
|
||||
|
||||
if file_name is None:
|
||||
# FIXME /dev/null crashes the data taking (h5py can't close /dev/null and crashes)
|
||||
#FIXME /dev/null crashes the data taking (h5py can't close /dev/null and crashes)
|
||||
print("Not saving any data, as file_name is not set")
|
||||
file_name_JF = file_rootdir + "DelMe" + '_JF4p5M.h5'
|
||||
file_name_bsread = file_rootdir + "DelMe" + '.h5'
|
||||
file_name_JF = file_rootdir + "DelMe" + "_JF4p5M.h5"
|
||||
file_name_bsread = file_rootdir + "DelMe" + ".h5"
|
||||
else:
|
||||
# FIXME hardcoded
|
||||
file_name_JF = file_rootdir + file_name + '_JF4p5M.h5'
|
||||
file_name_bsread = file_rootdir + file_name + '.h5'
|
||||
#FIXME hardcoded
|
||||
file_name_JF = file_rootdir + file_name + "_JF4p5M.h5"
|
||||
file_name_bsread = file_rootdir + file_name + ".h5"
|
||||
|
||||
if self.pgroup == 0:
|
||||
raise ValueError("Please use set_pgroup() to set a pgroup value.")
|
||||
@@ -338,22 +337,26 @@ class DIAClient:
|
||||
self.update_config()
|
||||
#self.detector_config.update({
|
||||
# 'cycles': n_frames})
|
||||
self.writer_config.update({
|
||||
'output_file': file_name_JF,
|
||||
# 'n_messages': n_frames
|
||||
})
|
||||
self.writer_config.update(
|
||||
{
|
||||
"output_file": file_name_JF,
|
||||
#'n_messages': n_frames
|
||||
}
|
||||
)
|
||||
#self.backend_config.update({
|
||||
# 'n_frames': n_frames})
|
||||
self.bsread_config.update({
|
||||
'output_file':file_name_bsread,
|
||||
# 'Npulses': Npulses + bsread_padding
|
||||
})
|
||||
|
||||
# self.reset()
|
||||
self.bsread_config.update(
|
||||
{
|
||||
"output_file": file_name_bsread,
|
||||
#'Npulses': Npulses + bsread_padding
|
||||
}
|
||||
)
|
||||
|
||||
# self.reset()
|
||||
if reset_before:
|
||||
print('Starting reset in acquire')
|
||||
print("Starting reset in acquire")
|
||||
self.reset()
|
||||
print('Just resetted in acquire')
|
||||
print("Just resetted in acquire")
|
||||
self.set_config()
|
||||
#print(self.get_config())
|
||||
self.client.start()
|
||||
@@ -363,20 +366,23 @@ class DIAClient:
|
||||
|
||||
while not done:
|
||||
stat = self.get_status()
|
||||
if stat['status'] =='IntegrationStatus.FINISHED':
|
||||
if stat["status"] == "IntegrationStatus.FINISHED":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.BSREAD_STILL_RUNNING':
|
||||
if stat["status"] == "IntegrationStatus.BSREAD_STILL_RUNNING":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.INITIALIZED':
|
||||
if stat["status"] == "IntegrationStatus.INITIALIZED":
|
||||
done = True
|
||||
if stat['status'] == 'IntegrationStatus.DETECTOR_STOPPED':
|
||||
if stat["status"] == "IntegrationStatus.DETECTOR_STOPPED":
|
||||
done = True
|
||||
sleep(.1)
|
||||
outputfilenames = [f'{file_name_JF}.{tcli.upper()}.h5' for tcli in self.active_clients]
|
||||
sleep(0.1)
|
||||
|
||||
outputfilenames = [f"{file_name_JF}.{tcli.upper()}.h5" for tcli in self.active_clients]
|
||||
|
||||
return Task(acquire, hold=False)
|
||||
|
||||
|
||||
def wait_done(self):
|
||||
# self.check_running()
|
||||
self.check_still_running()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
from data_api import get_data
|
||||
|
||||
|
||||
class DataApi:
|
||||
|
||||
def __init__(self):
|
||||
pass
|
||||
|
||||
def get_data(self):
|
||||
pass
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,28 +1,30 @@
|
||||
from slic.core.adjustable import PVAdjustable, PVEnumAdjustable
|
||||
from ..aliases import Alias, append_object_to_object
|
||||
|
||||
|
||||
class CameraBasler:
|
||||
|
||||
def __init__(self, pvname, name=None):
|
||||
self.pvname = pvname
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':INIT', name='initialize')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':CAMERA', name='running')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':BOARD', name='board_no')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':SERIALNR', name='serial_no')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':EXPOSURE', name='_exposure_time')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':ACQMODE', name='_acq_mode')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':RECMODE', name='_req_mode')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':STOREMODE', name='_store_mode')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':BINY', name='_binx')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':BINY', name='_biny')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':REGIONX_START', name='_roixmin')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':REGIONX_END', name='_roixmax')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':REGIONY_START', name='_roiymin')
|
||||
append_object_to_object(self, PVAdjustable, self.pvname+':REGIONY_END', name='_roiymax')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':SET_PARAM', name='_set_parameters')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':TRIGGER', name='trigger_on')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname+':TRIGGERSOURCE', name='trigger_source')
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":INIT", name="initialize")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":CAMERA", name="running")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":BOARD", name="board_no")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":SERIALNR", name="serial_no")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":EXPOSURE", name="_exposure_time")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":ACQMODE", name="_acq_mode")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":RECMODE", name="_req_mode")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":STOREMODE", name="_store_mode")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":BINY", name="_binx")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":BINY", name="_biny")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":REGIONX_START", name="_roixmin")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":REGIONX_END", name="_roixmax")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":REGIONY_START", name="_roiymin")
|
||||
append_object_to_object(self, PVAdjustable, self.pvname + ":REGIONY_END", name="_roiymax")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":SET_PARAM", name="_set_parameters")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":TRIGGER", name="trigger_on")
|
||||
append_object_to_object(self, PVEnumAdjustable, self.pvname + ":TRIGGERSOURCE", name="trigger_source")
|
||||
#append_object_to_object(self, PVEnumAdjustable, self.pvname+':TRIGGEREDGE', name='trigger_edge')
|
||||
|
||||
|
||||
|
||||
@@ -2,23 +2,24 @@ from epics import PV
|
||||
|
||||
|
||||
_status_messages = {
|
||||
-13 : 'invalid value (cannot convert to float). Move not attempted.',
|
||||
-12 : 'target value outside soft limits. Move not attempted.',
|
||||
-11 : 'drive PV is not connected: Move not attempted.',
|
||||
-8 : 'move started, but timed-out.',
|
||||
-7 : 'move started, timed-out, but appears done.',
|
||||
-5 : 'move started, unexpected return value from PV.put()',
|
||||
-4 : 'move-with-wait finished, soft limit violation seen',
|
||||
-3 : 'move-with-wait finished, hard limit violation seen',
|
||||
0 : 'move-with-wait finish OK.',
|
||||
0 : 'move-without-wait executed, not comfirmed',
|
||||
1 : 'move-without-wait executed, move confirmed' ,
|
||||
3 : 'move-without-wait finished, hard limit violation seen',
|
||||
4 : 'move-without-wait finished, soft limit violation seen',
|
||||
}
|
||||
-13: "invalid value (cannot convert to float). Move not attempted.",
|
||||
-12: "target value outside soft limits. Move not attempted.",
|
||||
-11: "drive PV is not connected: Move not attempted.",
|
||||
-8: "move started, but timed-out.",
|
||||
-7: "move started, timed-out, but appears done.",
|
||||
-5: "move started, unexpected return value from PV.put()",
|
||||
-4: "move-with-wait finished, soft limit violation seen",
|
||||
-3: "move-with-wait finished, hard limit violation seen",
|
||||
0: "move-with-wait finish OK.",
|
||||
0: "move-without-wait executed, not comfirmed",
|
||||
1: "move-without-wait executed, move confirmed",
|
||||
3: "move-without-wait finished, hard limit violation seen",
|
||||
4: "move-without-wait finished, soft limit violation seen"
|
||||
}
|
||||
|
||||
|
||||
class DummyMot:
|
||||
|
||||
def __init__(self):
|
||||
self._mot
|
||||
self.name = "Dummy Motor"
|
||||
@@ -28,32 +29,30 @@ class DummyMot:
|
||||
""" Adjustable convention"""
|
||||
motor_pos = self._stage.get_current_value()
|
||||
motor_pos -= self.delay_stage_offset
|
||||
delay = motor_pos*2.*3.33333333*1e-12
|
||||
delay = motor_pos * 2.0 * 3.33333333 * 1e-12
|
||||
return delay
|
||||
|
||||
def set_current_value(self, value):
|
||||
motor_pos = self.delay_to_motor(value) + self.delay_stage_offset
|
||||
self._stage.set_current_value(motor_pos)
|
||||
return (value, motor_pos)
|
||||
return (value, motor_pos)
|
||||
|
||||
def set_target_value(self, value, hold=False, check=True):
|
||||
value = self.delay_to_motor(value) + self.delay_stage_offset
|
||||
delay = (value - self.delay_stage_offset)*2.*3.33333333*1e-12
|
||||
delay = (value - self.delay_stage_offset) * 2.0 * 3.33333333 * 1e-12
|
||||
return self._stage.set_target_value(value, hold, check)
|
||||
|
||||
|
||||
def gui(self, guiType='xdm'):
|
||||
def gui(self, guiType="xdm"):
|
||||
return self._stage.gui()
|
||||
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._stage._currentChange = self.set_target_value(value)
|
||||
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
motor_pos = self.delay_to_motor(value)
|
||||
self._stage.mvr(motor_pos)
|
||||
|
||||
@@ -63,20 +62,20 @@ class DummyMot:
|
||||
def stop(self):
|
||||
""" Adjustable convention"""
|
||||
try:
|
||||
self._stage._currentChange.stop()
|
||||
self._stage._currentChange.stop()
|
||||
except:
|
||||
self._stage.stop()
|
||||
self._stage.stop()
|
||||
pass
|
||||
|
||||
|
||||
|
||||
# return string with motor value as variable representation
|
||||
def __str__(self):
|
||||
return "Motor is at %s"%self.wm()
|
||||
|
||||
return "Motor is at %s" % self.wm()
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
|
||||
class PowerSocket:
|
||||
|
||||
def __init__(self, pvname, name=None):
|
||||
self.alias = Alias(name)
|
||||
self.name = name
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -6,81 +6,90 @@ from ..eco_epics.device import Device
|
||||
from slic.core.task import Task
|
||||
|
||||
|
||||
_guiTypes = ['xdm']
|
||||
_guiTypes = ["xdm"]
|
||||
|
||||
|
||||
def _keywordChecker(kw_key_list_tups):
|
||||
for tkw,tkey,tlist in kw_key_list_tups:
|
||||
assert tkey in tlist, "Keyword %s should be one of %s"%(tkw,tlist)
|
||||
for tkw, tkey, tlist in kw_key_list_tups:
|
||||
assert tkey in tlist, "Keyword %s should be one of %s" % (tkw, tlist)
|
||||
|
||||
|
||||
class SmarActException(Exception):
|
||||
""" raised to indicate a problem with a smartact"""
|
||||
|
||||
def __init__(self, msg, *args):
|
||||
Exception.__init__(self, *args)
|
||||
self.msg = msg
|
||||
|
||||
def __str__(self):
|
||||
return str(self.msg)
|
||||
|
||||
return str(self.msg)
|
||||
|
||||
|
||||
class SmarAct(Device):
|
||||
_extras = {'disabled':'_able.VAL', }
|
||||
_init_list = ('VAL', 'DESC', 'RTYP')
|
||||
_nonpvs = ('_prefix', '_pvs', '_delim', '_init', '_init_list', '_alias', '_extras')
|
||||
|
||||
_extras = {
|
||||
"disabled": "_able.VAL",
|
||||
}
|
||||
_init_list = ("VAL", "DESC", "RTYP")
|
||||
_nonpvs = ("_prefix", "_pvs", "_delim", "_init", "_init_list", "_alias", "_extras")
|
||||
|
||||
def __init__(self, name=None, timeout=3.0, record=None):
|
||||
if name is None:
|
||||
raise SmarActException("must supply SmarAct name")
|
||||
|
||||
if name.endswith('.VAL'):
|
||||
if name.endswith(".VAL"):
|
||||
name = name[:-4]
|
||||
if name.endswith('.'):
|
||||
if name.endswith("."):
|
||||
name = name[:-1]
|
||||
|
||||
self._prefix = name
|
||||
self._record = record
|
||||
self._callbacks = {}
|
||||
|
||||
device.Device.__init__(self, name, delim='.',
|
||||
attrs=self._init_list,
|
||||
timeout=timeout)
|
||||
|
||||
device.Device.__init__(self, name, delim=".", attrs=self._init_list, timeout=timeout)
|
||||
|
||||
|
||||
# for key, val in self._extras.items():
|
||||
# pvname = "%s%s" % (name, val)
|
||||
# self.add_pv(pvname, attr=key)
|
||||
|
||||
# self.put('disabled', 0)
|
||||
|
||||
# self.put('disabled', 0)
|
||||
|
||||
|
||||
class SmarActRecord:
|
||||
def __init__(self,Id, name=None, elog=None):
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self._drive = SmarAct(Id+':DRIVE')
|
||||
self._rbv = SmarAct(Id+':MOTRBV')
|
||||
self._hlm = SmarAct(Id+':HLM')
|
||||
self._llm = SmarAct(Id+':LLM')
|
||||
self._status = SmarAct(Id+':STATUS')
|
||||
self._set_pos = SmarAct(Id+':SET_POS')
|
||||
self._stop = SmarAct(Id+':STOP')
|
||||
self._hold = SmarAct(Id+':HOLD')
|
||||
self._twv = SmarAct(Id+':TWV')
|
||||
self._drive = SmarAct(Id + ":DRIVE")
|
||||
self._rbv = SmarAct(Id + ":MOTRBV")
|
||||
self._hlm = SmarAct(Id + ":HLM")
|
||||
self._llm = SmarAct(Id + ":LLM")
|
||||
self._status = SmarAct(Id + ":STATUS")
|
||||
self._set_pos = SmarAct(Id + ":SET_POS")
|
||||
self._stop = SmarAct(Id + ":STOP")
|
||||
self._hold = SmarAct(Id + ":HOLD")
|
||||
self._twv = SmarAct(Id + ":TWV")
|
||||
self._elog = elog
|
||||
self.name = name
|
||||
self.units = self._drive.get('EGU')
|
||||
self.units = self._drive.get("EGU")
|
||||
|
||||
# Conventional methods and properties for all Adjustable objects
|
||||
def set_target_value(self, value, hold=False, check=True):
|
||||
""" Adjustable convention"""
|
||||
mover = lambda: self.move(value, ignore_limits=(not check), wait=True)
|
||||
return Task(mover, hold=hold, stopper=self._stop.put('PROC', 1))
|
||||
return Task(mover, hold=hold, stopper=self._stop.put("PROC", 1))
|
||||
|
||||
def stop(self):
|
||||
""" Adjustable convention"""
|
||||
try:
|
||||
self._currentChange.stop()
|
||||
self._currentChange.stop()
|
||||
except:
|
||||
self._stop.put('VAL',1)
|
||||
self._stop.put("VAL", 1)
|
||||
pass
|
||||
|
||||
def within_limits(self, val):
|
||||
""" returns whether a value for a motor is within drive limits"""
|
||||
return (val <= self._hlm.get('VAL') and val >= self._llm.get('VAL'))
|
||||
return val <= self._hlm.get("VAL") and val >= self._llm.get("VAL")
|
||||
|
||||
def move(self, val, relative=False, wait=False, timeout=300.0, ignore_limits=False, confirm_move=False):
|
||||
""" moves smaract drive to position
|
||||
@@ -111,56 +120,56 @@ class SmarActRecord:
|
||||
|
||||
"""
|
||||
NONFLOAT, OUTSIDE_LIMITS, UNCONNECTED = -13, -12, -11
|
||||
TIMEOUT = -8
|
||||
UNKNOWN_ERROR = -5
|
||||
DONE_OK = 0
|
||||
MOVE_BEGUN, MOVE_BEGUN_CONFIRMED = 0, 1
|
||||
TIMEOUT = -8
|
||||
UNKNOWN_ERROR = -5
|
||||
DONE_OK = 0
|
||||
MOVE_BEGUN, MOVE_BEGUN_CONFIRMED = 0, 1
|
||||
try:
|
||||
val = float(val)
|
||||
except TypeError:
|
||||
return NONFLOAT
|
||||
|
||||
if relative:
|
||||
val += self._drive.get('VAL')
|
||||
val += self._drive.get("VAL")
|
||||
|
||||
# Check for limit violations
|
||||
if not ignore_limits:
|
||||
if not self.within_limits(val):
|
||||
return OUTSIDE_LIMITS
|
||||
|
||||
stat = self._drive.put('VAL', val, wait=wait, timeout=timeout)
|
||||
stat = self._drive.put("VAL", val, wait=wait, timeout=timeout)
|
||||
if stat is None:
|
||||
return UNCONNECTED
|
||||
|
||||
|
||||
if wait and stat == -1:
|
||||
return TIMEOUT
|
||||
|
||||
if 1 == stat:
|
||||
s0 = self._status.get('VAL')
|
||||
s0 = self._status.get("VAL")
|
||||
s1 = s0
|
||||
t0 = time.time()
|
||||
t1 = t0 + min(10.0, timeout) # should be moving by now
|
||||
thold = self._hold.get('VAL') * 0.001 + t0
|
||||
t1 = t0 + min(10.0, timeout) # should be moving by now
|
||||
thold = self._hold.get("VAL") * 0.001 + t0
|
||||
tout = t0 + timeout
|
||||
if wait or confirm_move:
|
||||
while time.time() <= thold and s1 == 3:
|
||||
ca.poll(evt=1.e-2)
|
||||
s1 = self._status.get('VAL')
|
||||
ca.poll(evt=1.0e-2)
|
||||
s1 = self._status.get("VAL")
|
||||
while time.time() <= t1 and s1 == 0:
|
||||
ca.poll(evt=1.e-2)
|
||||
s1 = self._status.get('VAL')
|
||||
ca.poll(evt=1.0e-2)
|
||||
s1 = self._status.get("VAL")
|
||||
if s1 == 4:
|
||||
if wait:
|
||||
while time.time() <= tout and s1 == 4:
|
||||
ca.poll(evt=1.e-2)
|
||||
s1 = self._status.get('VAL')
|
||||
ca.poll(evt=1.0e-2)
|
||||
s1 = self._status.get("VAL")
|
||||
if s1 == 3 or s1 == 4:
|
||||
if time.time() > tout:
|
||||
return TIMEOUT
|
||||
else:
|
||||
twv = abs(self._twv.get('VAL'))
|
||||
while s1==3 and time.time()<=tout and abs(self._rbv.get('VAL')-val)>=twv:
|
||||
ca.poll(evt=1.e-2)
|
||||
twv = abs(self._twv.get("VAL"))
|
||||
while s1 == 3 and time.time() <= tout and abs(self._rbv.get("VAL") - val) >= twv:
|
||||
ca.poll(evt=1.0e-2)
|
||||
return DONE_OK
|
||||
else:
|
||||
return MOVE_BEGUN_CONFIRMED
|
||||
@@ -172,14 +181,14 @@ class SmarActRecord:
|
||||
return MOVE_BEGUN
|
||||
return UNKNOWN_ERROR
|
||||
|
||||
def get_current_value(self,readback=True):
|
||||
def get_current_value(self, readback=True):
|
||||
if readback:
|
||||
return self._rbv.get('VAL')
|
||||
else :
|
||||
return self._drive.get('VAL')
|
||||
return self._rbv.get("VAL")
|
||||
else:
|
||||
return self._drive.get("VAL")
|
||||
|
||||
def set_current_value(self,value):
|
||||
return self._set_pos.put('VAL',value)
|
||||
def set_current_value(self, value):
|
||||
return self._set_pos.put("VAL", value)
|
||||
|
||||
def get_precision(self):
|
||||
""" Adjustable convention"""
|
||||
@@ -189,14 +198,16 @@ class SmarActRecord:
|
||||
""" Adjustable convention"""
|
||||
pass
|
||||
|
||||
precision = property(get_precision,set_precision)
|
||||
precision = property(get_precision, set_precision)
|
||||
|
||||
def set_speed(self):
|
||||
""" Adjustable convention"""
|
||||
pass
|
||||
|
||||
def get_speed(self):
|
||||
""" Adjustable convention"""
|
||||
pass
|
||||
|
||||
def set_speedMax(self):
|
||||
""" Adjustable convention"""
|
||||
pass
|
||||
@@ -204,79 +215,84 @@ class SmarActRecord:
|
||||
def is_moving(self):
|
||||
pass
|
||||
|
||||
def set_limits(self, values, posType='user', relative_to_present=False):
|
||||
def set_limits(self, values, posType="user", relative_to_present=False):
|
||||
""" Adjustable convention"""
|
||||
if relative_to_present:
|
||||
v = self.get_current_value()
|
||||
values = [v-values[0],v-values[1]]
|
||||
self._llm.put('VAL',values[0])
|
||||
self._hlm.put('VAL',values[1])
|
||||
values = [v - values[0], v - values[1]]
|
||||
self._llm.put("VAL", values[0])
|
||||
self._hlm.put("VAL", values[1])
|
||||
|
||||
def get_limits(self, posType='user'):
|
||||
def get_limits(self, posType="user"):
|
||||
""" Adjustable convention"""
|
||||
return self._llm.get('VAL'), self._hlm.get('VAL')
|
||||
return self._llm.get("VAL"), self._hlm.get("VAL")
|
||||
|
||||
def gui(self, guiType='xdm'):
|
||||
def gui(self, guiType="xdm"):
|
||||
""" Adjustable convention"""
|
||||
cmd = ['caqtdm','-macro']
|
||||
cmd = ["caqtdm", "-macro"]
|
||||
|
||||
for i in range(len(self.Id)-1):
|
||||
if self.Id[-i-1].isnumeric() is False:
|
||||
for i in range(len(self.Id) - 1):
|
||||
if self.Id[-i - 1].isnumeric() is False:
|
||||
M = self.Id[-i:]
|
||||
P = self.Id[:-i]
|
||||
print(P, M)
|
||||
break
|
||||
|
||||
cmd.append('\"P=%s,M=%s\"'%(P, M))
|
||||
|
||||
cmd.append('"P=%s,M=%s"' % (P, M))
|
||||
# #cmd.append('/sf/common/config/qt/motorx_more.ui')
|
||||
cmd.append('ESB_MX_SMARACT_mot_exp.ui')
|
||||
cmd.append("ESB_MX_SMARACT_mot_exp.ui")
|
||||
# #os.system(' '.join(cmd))
|
||||
return subprocess.Popen(' '.join(cmd),shell=True)
|
||||
return subprocess.Popen(" ".join(cmd), shell=True)
|
||||
|
||||
|
||||
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
startvalue = self.get_current_value(readback=True,*args,**kwargs)
|
||||
self._currentChange = self.set_target_value(value+startvalue,*args,**kwargs)
|
||||
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
startvalue = self.get_current_value(readback=True, *args, **kwargs)
|
||||
self._currentChange = self.set_target_value(value + startvalue, *args, **kwargs)
|
||||
|
||||
def wait(self):
|
||||
self._currentChange.wait()
|
||||
|
||||
|
||||
# return string with motor value as variable representation
|
||||
def __str__(self):
|
||||
return "SmarAct is at %s"%(self.wm())
|
||||
return "SmarAct is at %s" % (self.wm())
|
||||
#return "SmarAct is at %s %s"%(self.wm(),self.units)
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
class SmarActDevice(SmarActRecord):
|
||||
def __init__(self,Id,alias_namespace=None):
|
||||
|
||||
def __init__(self, Id, alias_namespace=None):
|
||||
SmarActRecord.__init__(self, Id)
|
||||
|
||||
|
||||
# self.Id = Id
|
||||
#
|
||||
# self.x = SmarActRecord(Id+':DRIVE')
|
||||
|
||||
|
||||
class SmarActStage:
|
||||
|
||||
def __init__(self, axes, name):
|
||||
self._keys = axes.keys()
|
||||
for axis in self._keys:
|
||||
self.__dict__[axis] = axes[axis]
|
||||
self.name = name
|
||||
|
||||
|
||||
def __str__(self):
|
||||
return "SmarAct positions\n%s" % "\n".join(["%s: %s"%(key,self.__dict__[key].wm()) for key in self._keys])
|
||||
|
||||
return "SmarAct positions\n%s" % "\n".join(["%s: %s" % (key, self.__dict__[key].wm()) for key in self._keys])
|
||||
|
||||
def __repr__(self):
|
||||
return str({key:self.__dict__[key].wm() for key in self._keys})
|
||||
return str({key: self.__dict__[key].wm() for key in self._keys})
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -2,23 +2,24 @@ from epics import PV
|
||||
|
||||
|
||||
_status_messages = {
|
||||
-13: "invalid value (cannot convert to float). Move not attempted.",
|
||||
-12: "target value outside soft limits. Move not attempted.",
|
||||
-11: "drive PV is not connected: Move not attempted.",
|
||||
-8: "move started, but timed-out.",
|
||||
-7: "move started, timed-out, but appears done.",
|
||||
-5: "move started, unexpected return value from PV.put()",
|
||||
-4: "move-with-wait finished, soft limit violation seen",
|
||||
-3: "move-with-wait finished, hard limit violation seen",
|
||||
0: "move-with-wait finish OK.",
|
||||
0: "move-without-wait executed, not comfirmed",
|
||||
1: "move-without-wait executed, move confirmed",
|
||||
3: "move-without-wait finished, hard limit violation seen",
|
||||
4: "move-without-wait finished, soft limit violation seen",
|
||||
-13: "invalid value (cannot convert to float). Move not attempted.",
|
||||
-12: "target value outside soft limits. Move not attempted.",
|
||||
-11: "drive PV is not connected: Move not attempted.",
|
||||
-8: "move started, but timed-out.",
|
||||
-7: "move started, timed-out, but appears done.",
|
||||
-5: "move started, unexpected return value from PV.put()",
|
||||
-4: "move-with-wait finished, soft limit violation seen",
|
||||
-3: "move-with-wait finished, hard limit violation seen",
|
||||
0: "move-with-wait finish OK.",
|
||||
0: "move-without-wait executed, not comfirmed",
|
||||
1: "move-without-wait executed, move confirmed",
|
||||
3: "move-without-wait finished, hard limit violation seen",
|
||||
4: "move-without-wait finished, soft limit violation seen",
|
||||
}
|
||||
|
||||
|
||||
class User_to_motor:
|
||||
|
||||
def __init__(self, stage, conversion_conv, offset):
|
||||
self.conv = conversion_conv
|
||||
self._stage = stage
|
||||
@@ -82,3 +83,6 @@ class User_to_motor:
|
||||
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@ import colorama
|
||||
|
||||
|
||||
def update_changes(Adj):
|
||||
|
||||
def get_position_str(start, end, value):
|
||||
s = ValueInRange(start, end, bar_width=30, unit="", fmt="1.5g").get_str(value)
|
||||
return (
|
||||
@@ -16,9 +15,7 @@ def update_changes(Adj):
|
||||
|
||||
def update_change(self, value):
|
||||
start = self.get_current_value()
|
||||
print(
|
||||
f"Changing {self.name} from {start:1.5g} by {value-start:1.5g} to {value:1.5g}\n"
|
||||
)
|
||||
print(f"Changing {self.name} from {start:1.5g} by {value-start:1.5g} to {value:1.5g}\n")
|
||||
print(get_position_str(start, value, start), end="\r")
|
||||
try:
|
||||
|
||||
@@ -51,7 +48,6 @@ def update_changes(Adj):
|
||||
return Adj
|
||||
|
||||
|
||||
|
||||
class ValueInRange:
|
||||
|
||||
def __init__(self, start_value, end_value, bar_width=30, unit="", fmt="1.5g"):
|
||||
|
||||
@@ -7,7 +7,6 @@ from ..general.delay_stage import DelayStage
|
||||
from ..timing.alvralasertiming import eTiming
|
||||
|
||||
|
||||
|
||||
class LaserExp(BaseDevice):
|
||||
"""Experiment laser hardware"""
|
||||
|
||||
@@ -53,7 +52,6 @@ class LaserExp(BaseDevice):
|
||||
# Globi electronic timing PV from Edwin
|
||||
self.eTiming = eTiming(Id + "-eTiming")
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
to_print = {}
|
||||
for key, item in self.__dict__.items():
|
||||
|
||||
@@ -1,26 +1,29 @@
|
||||
from epics import caput, caget
|
||||
|
||||
|
||||
class laser_shutter:
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
def __repr__(self):
|
||||
return self.get_status()
|
||||
|
||||
def get_status(self):
|
||||
Id = self.Id
|
||||
status = caget(Id+":SET_BO02")
|
||||
if status == 0:
|
||||
return 'open'
|
||||
elif status == 1:
|
||||
return 'close'
|
||||
else:
|
||||
return "unknown"
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
def __repr__(self):
|
||||
return self.get_status()
|
||||
|
||||
def get_status(self):
|
||||
Id = self.Id
|
||||
status = caget(Id + ":SET_BO02")
|
||||
if status == 0:
|
||||
return "open"
|
||||
elif status == 1:
|
||||
return "close"
|
||||
else:
|
||||
return "unknown"
|
||||
|
||||
def open(self):
|
||||
caput(self.Id + ":SET_BO02", 0)
|
||||
|
||||
def close(self):
|
||||
caput(self.Id + ":SET_BO02", 1)
|
||||
|
||||
def open(self):
|
||||
caput(self.Id+":SET_BO02",0)
|
||||
|
||||
def close(self):
|
||||
caput(self.Id+":SET_BO02",1)
|
||||
|
||||
|
||||
|
||||
@@ -8,6 +8,7 @@ from ..general.adjustable import AdjustableVirtual
|
||||
|
||||
import colorama, datetime
|
||||
from pint import UnitRegistry
|
||||
|
||||
ureg = UnitRegistry()
|
||||
|
||||
|
||||
@@ -27,6 +28,7 @@ def addDelayStageToSelf(self, stage=None, name=None):
|
||||
|
||||
|
||||
class DelayTime(AdjustableVirtual):
|
||||
|
||||
def __init__(self, stage, direction=1, passes=2, reset_current_value_to=True, name=None):
|
||||
self._direction = direction
|
||||
self._group_velo = 299798458 # m/s
|
||||
@@ -34,12 +36,7 @@ class DelayTime(AdjustableVirtual):
|
||||
self.Id = stage.Id + "_delay"
|
||||
self._stage = stage
|
||||
AdjustableVirtual.__init__(
|
||||
self,
|
||||
[stage],
|
||||
self._mm_to_s,
|
||||
self._s_to_mm,
|
||||
reset_current_value_to=reset_current_value_to,
|
||||
name=name,
|
||||
self, [stage], self._mm_to_s, self._s_to_mm, reset_current_value_to=reset_current_value_to, name=name,
|
||||
)
|
||||
|
||||
def _mm_to_s(self, mm):
|
||||
@@ -49,26 +46,26 @@ class DelayTime(AdjustableVirtual):
|
||||
return s * self._group_velo * 1e3 / self._passes * self._direction
|
||||
|
||||
def __repr__(self):
|
||||
s = ''
|
||||
s = ""
|
||||
s += f"{colorama.Style.DIM}"
|
||||
s += datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')+': '
|
||||
s += datetime.datetime.now().strftime("%Y/%m/%d %H:%M:%S") + ": "
|
||||
s += f"{colorama.Style.RESET_ALL}"
|
||||
s += f"{colorama.Style.BRIGHT}{self._get_name()}{colorama.Style.RESET_ALL} at "
|
||||
s += f'{(self.get_current_value()*ureg.second).to_compact():P~6.3f}'
|
||||
s += f"{(self.get_current_value()*ureg.second).to_compact():P~6.3f}"
|
||||
s += f"{colorama.Style.RESET_ALL}"
|
||||
return s
|
||||
|
||||
def get_limits(self):
|
||||
return [self._mm_to_s(tl) for tl in self._stage.get_limits()]
|
||||
|
||||
def set_limits(self,low_limit,high_limit):
|
||||
lims_stage = [self._s_to_mm(tl) for tl in [low_limit,high_limit]]
|
||||
def set_limits(self, low_limit, high_limit):
|
||||
lims_stage = [self._s_to_mm(tl) for tl in [low_limit, high_limit]]
|
||||
lims_stage.sort()
|
||||
self._stage.set_limits(*lims_stage)
|
||||
|
||||
|
||||
return [self._mm_to_s(tl) for tl in self._stage.get_limits()]
|
||||
|
||||
|
||||
class DelayCompensation(AdjustableVirtual):
|
||||
"""Simple virtual adjustable for compensating delay adjustables. It assumes the first adjustable is the master for
|
||||
getting the current value."""
|
||||
@@ -77,12 +74,7 @@ class DelayCompensation(AdjustableVirtual):
|
||||
self._directions = directions
|
||||
self.Id = name
|
||||
AdjustableVirtual.__init__(
|
||||
self,
|
||||
adjustables,
|
||||
self._from_values,
|
||||
self._calc_values,
|
||||
set_current_value = set_current_value,
|
||||
name=name,
|
||||
self, adjustables, self._from_values, self._calc_values, set_current_value=set_current_value, name=name,
|
||||
)
|
||||
|
||||
def _calc_values(self, value):
|
||||
@@ -93,19 +85,20 @@ class DelayCompensation(AdjustableVirtual):
|
||||
return positions[0]
|
||||
|
||||
tuple(tdir * value for tdir in self._directions)
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
s = ''
|
||||
s = ""
|
||||
s += f"{colorama.Style.DIM}"
|
||||
s += datetime.datetime.now().strftime('%Y/%m/%d %H:%M:%S')+': '
|
||||
s += datetime.datetime.now().strftime("%Y/%m/%d %H:%M:%S") + ": "
|
||||
s += f"{colorama.Style.RESET_ALL}"
|
||||
s += f"{colorama.Style.BRIGHT}{self._get_name()}{colorama.Style.RESET_ALL} at "
|
||||
s += f'{(self.get_current_value()*ureg.second).to_compact():P~6.3f}'
|
||||
s += f"{(self.get_current_value()*ureg.second).to_compact():P~6.3f}"
|
||||
s += f"{colorama.Style.RESET_ALL}"
|
||||
return s
|
||||
|
||||
|
||||
class Laser_Exp:
|
||||
|
||||
def __init__(self, Id=None, name=None, smar_config=None):
|
||||
self.Id = Id
|
||||
self.IdExp1 = "SARES20-EXP"
|
||||
@@ -122,12 +115,8 @@ class Laser_Exp:
|
||||
print("No wp found")
|
||||
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M521:MOTOR_1", name="_pump_delaystg"
|
||||
)
|
||||
addDelayStageToSelf(
|
||||
self, stage=self.__dict__["_pump_delaystg"], name="pump_delay"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M521:MOTOR_1", name="_pump_delaystg")
|
||||
addDelayStageToSelf(self, stage=self.__dict__["_pump_delaystg"], name="pump_delay")
|
||||
except Exception as expt:
|
||||
print("No eos delay stage")
|
||||
print(expt)
|
||||
@@ -136,24 +125,20 @@ class Laser_Exp:
|
||||
addMotorToSelf(self, Id=self.Id + "-M521:MOTOR_1", name="delay_eos_stg")
|
||||
self.delay_eos = DelayTime(self.delay_eos_stg, name="delay_eos")
|
||||
self.alias.append(self.delay_eos.alias)
|
||||
self.lxt_eos = DelayTime(self.delay_eos_stg, direction=-1,name="lxt_eos")
|
||||
self.lxt_eos = DelayTime(self.delay_eos_stg, direction=-1, name="lxt_eos")
|
||||
self.alias.append(self.lxt_eos.alias)
|
||||
# except Exception as expt:
|
||||
# print("Problems initializing eos delay stage")
|
||||
# print(expt)
|
||||
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M522:MOTOR_1", name="delay_tt_stg"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M522:MOTOR_1", name="delay_tt_stg")
|
||||
self.delay_tt = DelayTime(self.delay_tt_stg, name="delay_tt")
|
||||
self.alias.append(self.delay_tt.alias)
|
||||
except:
|
||||
print("Problems initializing global delay stage")
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M523:MOTOR_1", name="delay_glob_stg"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M523:MOTOR_1", name="delay_glob_stg")
|
||||
self.delay_glob = DelayTime(self.delay_glob_stg, name="delay_glob")
|
||||
self.alias.append(self.delay_glob.alias)
|
||||
self.lxt_glob = DelayTime(self.delay_glob_stg, direction=-1, name="lxt_glob")
|
||||
@@ -163,21 +148,17 @@ class Laser_Exp:
|
||||
|
||||
# Implementation of delay compensation, this assumes for now that delays_glob and delay_tt actually delay in positive directions.
|
||||
try:
|
||||
self.delay_lxtt = DelayCompensation(
|
||||
[self.delay_glob, self.delay_tt], [-1, 1], name="delay_lxtt"
|
||||
)
|
||||
self.delay_lxtt = DelayCompensation([self.delay_glob, self.delay_tt], [-1, 1], name="delay_lxtt")
|
||||
self.alias.append(self.delay_lxtt.alias)
|
||||
except:
|
||||
print('Problems initializing virtual pump delay stage')
|
||||
except:
|
||||
print("Problems initializing virtual pump delay stage")
|
||||
# compressor
|
||||
addMotorToSelf(self, Id=self.Id + "-M532:MOT", name="compressor")
|
||||
# self.compressor = Motor(Id+'-M532:MOT')
|
||||
|
||||
# LAM delay stages
|
||||
addSmarActRecordToSelf(self, Id="SLAAR21-LMTS-LAM11", name="_lam_delay_smarstg")
|
||||
addDelayStageToSelf(
|
||||
self, self.__dict__["_lam_delay_smarstg"], name="lam_delay_smar"
|
||||
)
|
||||
addDelayStageToSelf(self, self.__dict__["_lam_delay_smarstg"], name="lam_delay_smar")
|
||||
# self._lam_delayStg_Smar = SmarActRecord('SLAAR21-LMTS-LAM11')
|
||||
# self.lam_delay_Smar = DelayStage(self._lam_delayStg_Smar)
|
||||
|
||||
@@ -196,12 +177,8 @@ class Laser_Exp:
|
||||
# self._psen_delayStg = Motor(self.Id+'')
|
||||
# self.psen_delay = DelayStage(self._pump_delayStg)
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M561:MOT", name="_psen_delaystg"
|
||||
)
|
||||
addDelayStageToSelf(
|
||||
self, stage=self.__dict__["_psen_delaystg"], name="psen_delay"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M561:MOT", name="_psen_delaystg")
|
||||
addDelayStageToSelf(self, stage=self.__dict__["_psen_delaystg"], name="psen_delay")
|
||||
except Exception as expt:
|
||||
print("No psen delay stage")
|
||||
print(expt)
|
||||
@@ -211,14 +188,9 @@ class Laser_Exp:
|
||||
|
||||
for smar_name, smar_address in self.smar_config.items():
|
||||
try:
|
||||
addSmarActRecordToSelf(
|
||||
self, Id=(self.IdSA + smar_address), name=smar_name
|
||||
)
|
||||
addSmarActRecordToSelf(self, Id=(self.IdSA + smar_address), name=smar_name)
|
||||
except:
|
||||
print("Loading %s SmarAct motor in bernina laser conifg failed") % (
|
||||
smar_name
|
||||
)
|
||||
pass
|
||||
print("Loading %s SmarAct motor in bernina laser conifg failed") % (smar_name)
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = "*****Laser motor positions******\n"
|
||||
@@ -226,10 +198,10 @@ class Laser_Exp:
|
||||
for tkey, item in sorted(self.__dict__.items()):
|
||||
if hasattr(item, "get_current_value"):
|
||||
pos = item.get_current_value()
|
||||
posdialstr = ''
|
||||
posdialstr = ""
|
||||
try:
|
||||
posdial = item.get_current_value(postype = 'dial')
|
||||
posdialstr = ' dial: % 14g\n' % posdial
|
||||
posdial = item.get_current_value(postype="dial")
|
||||
posdialstr = " dial: % 14g\n" % posdial
|
||||
except:
|
||||
pass
|
||||
ostr += " " + tkey.ljust(18) + " : % 14g\n" % pos + posdialstr
|
||||
@@ -240,6 +212,7 @@ class Laser_Exp:
|
||||
|
||||
|
||||
class Laser_Exp_old:
|
||||
|
||||
def __init__(self, Id=None, name=None, smar_config=None):
|
||||
self.Id = Id
|
||||
self.IdExp1 = "SARES20-EXP"
|
||||
@@ -256,19 +229,13 @@ class Laser_Exp_old:
|
||||
print("No wp found")
|
||||
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M521:MOTOR_1", name="_pump_delaystg"
|
||||
)
|
||||
addDelayStageToSelf(
|
||||
self, stage=self.__dict__["_pump_delaystg"], name="pump_delay"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M521:MOTOR_1", name="_pump_delaystg")
|
||||
addDelayStageToSelf(self, stage=self.__dict__["_pump_delaystg"], name="pump_delay")
|
||||
except:
|
||||
print("No eos delay stage")
|
||||
pass
|
||||
try:
|
||||
addMotorToSelf(
|
||||
self, Id=self.Id + "-M522:MOTOR_1", name="_tt_delaystg"
|
||||
)
|
||||
addMotorToSelf(self, Id=self.Id + "-M522:MOTOR_1", name="_tt_delaystg")
|
||||
addDelayStageToSelf(self, self.__dict__["_tt_delaystg"], name="tt_delay")
|
||||
# addDelayStageToSelf(self,self.__dict__["_thz_delaystg"], name="thz_delay")
|
||||
except:
|
||||
@@ -288,9 +255,7 @@ class Laser_Exp_old:
|
||||
|
||||
# LAM delay stages
|
||||
addSmarActRecordToSelf(self, Id="SLAAR21-LMTS-LAM11", name="_lam_delay_smarstg")
|
||||
addDelayStageToSelf(
|
||||
self, self.__dict__["_lam_delay_smarstg"], name="lam_delay_smar"
|
||||
)
|
||||
addDelayStageToSelf(self, self.__dict__["_lam_delay_smarstg"], name="lam_delay_smar")
|
||||
# self._lam_delayStg_Smar = SmarActRecord('SLAAR21-LMTS-LAM11')
|
||||
# self.lam_delay_Smar = DelayStage(self._lam_delayStg_Smar)
|
||||
|
||||
@@ -314,14 +279,9 @@ class Laser_Exp_old:
|
||||
|
||||
for smar_name, smar_address in self.smar_config.items():
|
||||
try:
|
||||
addSmarActRecordToSelf(
|
||||
self, Id=(self.IdSA + smar_address), name=smar_name
|
||||
)
|
||||
addSmarActRecordToSelf(self, Id=(self.IdSA + smar_address), name=smar_name)
|
||||
except:
|
||||
print("Loading %s SmarAct motor in bernina laser conifg failed") % (
|
||||
smar_name
|
||||
)
|
||||
pass
|
||||
print("Loading %s SmarAct motor in bernina laser conifg failed") % (smar_name)
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = "*****Laser motor positions******\n"
|
||||
@@ -329,10 +289,10 @@ class Laser_Exp_old:
|
||||
for tkey, item in sorted(self.__dict__.items()):
|
||||
if hasattr(item, "get_current_value"):
|
||||
pos = item.get_current_value()
|
||||
posdialstr = ''
|
||||
posdialstr = ""
|
||||
try:
|
||||
posdial = item.get_current_value(postype = 'dial')
|
||||
posdialstr = ' dial: % 14g\n' % posdial
|
||||
posdial = item.get_current_value(postype="dial")
|
||||
posdialstr = " dial: % 14g\n" % posdial
|
||||
except:
|
||||
pass
|
||||
ostr += " " + tkey.ljust(18) + " : % 14g\n" % pos + posdialstr
|
||||
|
||||
@@ -2,6 +2,7 @@ from epics import caput, caget
|
||||
|
||||
|
||||
class laser_shutter:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
@@ -23,3 +24,6 @@ class laser_shutter:
|
||||
|
||||
def close(self):
|
||||
caput(self.Id + ":FrontUnivOut3_SOURCE", 3)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,21 +1,22 @@
|
||||
from ...general.smaract import SmarActRecord
|
||||
from epics import PV
|
||||
|
||||
|
||||
class SmaractTower:
|
||||
def __init__(self,Id):
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
### Mirrors used in the expeirment ###
|
||||
### Mirrors used in the experiment ###
|
||||
try:
|
||||
self.x = SmarActRecord(Id+'-ESB1')
|
||||
self.x = SmarActRecord(Id + "-ESB1")
|
||||
except:
|
||||
print('No Smaract x linear stage')
|
||||
pass
|
||||
print("No Smaract x linear stage")
|
||||
|
||||
try:
|
||||
self.gonio = SmarActRecord(Id+'-ESB2')
|
||||
self.gonio = SmarActRecord(Id + "-ESB2")
|
||||
except:
|
||||
print('No Smaract Gonio')
|
||||
pass
|
||||
print("No Smaract Gonio")
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3,6 +3,7 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class Laser_Exp:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
|
||||
@@ -7,44 +7,47 @@ from slic.core.task import Task
|
||||
|
||||
_basefolder = "/sf/alvra/config/lasertiming"
|
||||
|
||||
def timeToStr(value,n=12):
|
||||
|
||||
def timeToStr(value, n=12):
|
||||
fmt = "%%+.%df" % n
|
||||
value = fmt%value
|
||||
value = fmt % value
|
||||
#print(value)
|
||||
idx_point = value.find(".")
|
||||
ret_str = value[:idx_point] + " ."
|
||||
ngroups = (len(value)-idx_point)//3
|
||||
ngroups = (len(value) - idx_point) // 3
|
||||
for n in range(ngroups):
|
||||
ret_str += " %s" % value[idx_point+1+3*n:idx_point+1+3*(n+1)]
|
||||
#print(idx_point+1+3*n,idx_point+1*3*(n-1),ret_str)
|
||||
ret_str += " %s" % value[idx_point + 1 + 3 * n : idx_point + 1 + 3 * (n + 1)]
|
||||
#print(idx_point+1+3*n,idx_point+1*3*(n-1),ret_str)
|
||||
return ret_str
|
||||
|
||||
def niceTimeToStr(delay,fmt="%+.0f"):
|
||||
a_delay = abs(delay)
|
||||
if a_delay >= 1:
|
||||
ret = fmt % delay + "s"
|
||||
elif 1e-3 <= a_delay < 1:
|
||||
ret = fmt % (delay*1e3) + "ms"
|
||||
elif 1e-6 <= a_delay < 1e-3:
|
||||
ret = fmt % (delay*1e6) + "us"
|
||||
elif 1e-9 <= a_delay < 1e-6:
|
||||
ret = fmt % (delay*1e9) + "ns"
|
||||
elif 1e-12 <= a_delay < 1e-9:
|
||||
ret = fmt % (delay*1e12) + "ps"
|
||||
elif 1e-15 <= a_delay < 1e-12:
|
||||
ret = fmt % (delay*1e12) + "fs"
|
||||
elif 1e-18 <= a_delay < 1e-15:
|
||||
ret = fmt % (delay*1e12) + "as"
|
||||
elif a_delay < 1e-18:
|
||||
ret = "0s"
|
||||
else:
|
||||
ret = str(delay) +"s"
|
||||
return ret
|
||||
|
||||
def niceTimeToStr(delay, fmt="%+.0f"):
|
||||
a_delay = abs(delay)
|
||||
if a_delay >= 1:
|
||||
ret = fmt % delay + "s"
|
||||
elif 1e-3 <= a_delay < 1:
|
||||
ret = fmt % (delay * 1e3) + "ms"
|
||||
elif 1e-6 <= a_delay < 1e-3:
|
||||
ret = fmt % (delay * 1e6) + "us"
|
||||
elif 1e-9 <= a_delay < 1e-6:
|
||||
ret = fmt % (delay * 1e9) + "ns"
|
||||
elif 1e-12 <= a_delay < 1e-9:
|
||||
ret = fmt % (delay * 1e12) + "ps"
|
||||
elif 1e-15 <= a_delay < 1e-12:
|
||||
ret = fmt % (delay * 1e12) + "fs"
|
||||
elif 1e-18 <= a_delay < 1e-15:
|
||||
ret = fmt % (delay * 1e12) + "as"
|
||||
elif a_delay < 1e-18:
|
||||
ret = "0s"
|
||||
else:
|
||||
ret = str(delay) + "s"
|
||||
return ret
|
||||
|
||||
|
||||
class Storage(object):
|
||||
def __init__(self,pvname):
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
|
||||
def __init__(self, pvname):
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self.pvname = pvname
|
||||
self.last_read_time = -1
|
||||
|
||||
@@ -60,7 +63,7 @@ class Storage(object):
|
||||
lmod = self.last_modified_time
|
||||
if os.path.isfile(self._filename):
|
||||
# need to read again ?
|
||||
if self.last_read_time == -1 or lmod > self.last_read_time :
|
||||
if self.last_read_time == -1 or lmod > self.last_read_time:
|
||||
#print("actually reading")
|
||||
value = float(np.loadtxt(self._filename))
|
||||
self.last_read_time = lmod
|
||||
@@ -68,133 +71,142 @@ class Storage(object):
|
||||
else:
|
||||
value = self.last_read
|
||||
else:
|
||||
print("could not read",self._filename)
|
||||
print("could not read", self._filename)
|
||||
value = 0
|
||||
return value
|
||||
|
||||
def store(self,value):
|
||||
with open(self._filename,"w") as f:
|
||||
f.write("# %s\n"%time.asctime())
|
||||
f.write("%.15f"%value)
|
||||
def store(self, value):
|
||||
with open(self._filename, "w") as f:
|
||||
f.write("# %s\n" % time.asctime())
|
||||
f.write("%.15f" % value)
|
||||
|
||||
|
||||
class Pockels_trigger(PV):
|
||||
""" this class is needed to store the offset in files and read in s """
|
||||
def __init__(self,pv_basename):
|
||||
|
||||
def __init__(self, pv_basename):
|
||||
pvname = pv_basename + "-RB"
|
||||
PV.__init__(self,pvname)
|
||||
PV.__init__(self, pvname)
|
||||
self._pv_setvalue = PV(pv_basename + "-SP")
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
self._storage = Storage(pvname)
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self._storage = Storage(pvname)
|
||||
|
||||
@property
|
||||
def offset(self): return self._storage.value
|
||||
def offset(self):
|
||||
return self._storage.value
|
||||
|
||||
def get_dial(self):
|
||||
return np.round(super().get()*1e-6,9)
|
||||
return np.round(super().get() * 1e-6, 9)
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
return self.get_dial()-self.offset
|
||||
return self.get_dial() - self.offset
|
||||
|
||||
def store(self,value=None):
|
||||
if value == None: value = self.get_dial()
|
||||
self._storage.store( value )
|
||||
def store(self, value=None):
|
||||
if value == None:
|
||||
value = self.get_dial()
|
||||
self._storage.store(value)
|
||||
|
||||
def move(self,value):
|
||||
def move(self, value):
|
||||
dial = value + self.offset
|
||||
self._pv_setvalue.put(dial*1e6)
|
||||
self._pv_setvalue.put(dial * 1e6)
|
||||
|
||||
def set(self,value):
|
||||
newoffset = self.get_dial()-value
|
||||
def set(self, value):
|
||||
newoffset = self.get_dial() - value
|
||||
self.store(newoffset)
|
||||
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
dial = timeToStr( self.get_dial(),n=12 )
|
||||
user = timeToStr( self.get(),n=12 )
|
||||
return "Pockel Trigger PV: %s user , dial = %s, %s"%(self.pvname,user,dial)
|
||||
dial = timeToStr(self.get_dial(), n=12)
|
||||
user = timeToStr(self.get(), n=12)
|
||||
return "Pockel Trigger PV: %s user , dial = %s, %s" % (self.pvname, user, dial)
|
||||
|
||||
|
||||
_OSCILLATOR_PERIOD = 1 / 71.368704e6
|
||||
|
||||
_OSCILLATOR_PERIOD = 1/71.368704e6
|
||||
|
||||
class Phase_shifter(PV):
|
||||
""" this class is needed to store the offset in files and read in ps """
|
||||
def __init__(self,pv_basename="SLAAR01-TSPL-EPL",dial_max=14.0056e-9,precision=100e-15):
|
||||
pvname = pv_basename+":CURR_DELTA_T"
|
||||
PV.__init__(self,pvname)
|
||||
self._filename = os.path.join(_basefolder,pvname)
|
||||
|
||||
def __init__(self, pv_basename="SLAAR01-TSPL-EPL", dial_max=14.0056e-9, precision=100e-15):
|
||||
pvname = pv_basename + ":CURR_DELTA_T"
|
||||
PV.__init__(self, pvname)
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
self._pv_setvalue = PV(pv_basename + ":NEW_DELTA_T")
|
||||
self._pv_execute = PV(pv_basename + ":SET_NEW_PHASE.PROC")
|
||||
self._storage = Storage(pvname)
|
||||
self.dial_max = dial_max
|
||||
self._pv_execute = PV(pv_basename + ":SET_NEW_PHASE.PROC")
|
||||
self._storage = Storage(pvname)
|
||||
self.dial_max = dial_max
|
||||
self.retry = precision
|
||||
|
||||
@property
|
||||
def offset(self): return self._storage.value
|
||||
|
||||
def offset(self):
|
||||
return self._storage.value
|
||||
|
||||
def get_dial(self):
|
||||
return super().get()*1e-12
|
||||
return super().get() * 1e-12
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
return self.get_dial()-self.offset
|
||||
return self.get_dial() - self.offset
|
||||
|
||||
def store(self,value=None):
|
||||
if value == None: value = self.get_dial()
|
||||
self._storage.store( value )
|
||||
def store(self, value=None):
|
||||
if value == None:
|
||||
value = self.get_dial()
|
||||
self._storage.store(value)
|
||||
|
||||
def move(self,value,accuracy=None):
|
||||
if accuracy is None: accuracy = self.retry
|
||||
def move(self, value, accuracy=None):
|
||||
if accuracy is None:
|
||||
accuracy = self.retry
|
||||
dial = value + self.offset
|
||||
dial = np.mod(dial,_OSCILLATOR_PERIOD)
|
||||
if dial > self.dial_max: dial = self.dial_max
|
||||
dial_ps = dial*1e12
|
||||
dial = np.mod(dial, _OSCILLATOR_PERIOD)
|
||||
if dial > self.dial_max:
|
||||
dial = self.dial_max
|
||||
dial_ps = dial * 1e12
|
||||
self._pv_setvalue.put(dial_ps)
|
||||
time.sleep(0.1)
|
||||
self._pv_execute.put(1)
|
||||
#print(accuracy)
|
||||
while( np.abs(self.get_dial()-dial) > accuracy ):
|
||||
while np.abs(self.get_dial() - dial) > accuracy:
|
||||
#print(np.abs(self.get_dial()-dial))
|
||||
time.sleep(0.2)
|
||||
|
||||
def set(self,value):
|
||||
newoffset = self.get_dial()-value
|
||||
newoffset = np.mod(newoffset,_OSCILLATOR_PERIOD)
|
||||
def set(self, value):
|
||||
newoffset = self.get_dial() - value
|
||||
newoffset = np.mod(newoffset, _OSCILLATOR_PERIOD)
|
||||
self.store(newoffset)
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
dial = timeToStr( self.get_dial(),n=15 )
|
||||
user = timeToStr( self.get(),n=15 )
|
||||
return "Phase Shifter: user,dial = %s , %s"%(user,dial)
|
||||
dial = timeToStr(self.get_dial(), n=15)
|
||||
user = timeToStr(self.get(), n=15)
|
||||
return "Phase Shifter: user,dial = %s , %s" % (user, dial)
|
||||
|
||||
|
||||
_slicer_gate = Pockels_trigger("SLAAR-LTIM01-EVR0:Pul2-Delay")
|
||||
_slicer_gate = Pockels_trigger("SLAAR-LTIM01-EVR0:Pul2-Delay")
|
||||
_sdg1 = Pockels_trigger("SLAAR-LTIM01-EVR0:Pul3-Delay")
|
||||
_phase_shifter = Phase_shifter("SLAAR01-TSPL-EPL")
|
||||
|
||||
|
||||
_POCKELS_CELL_RESOLUTION = 7e-9
|
||||
|
||||
|
||||
class Lxt(object):
|
||||
|
||||
def __init__(self):
|
||||
self.sdg1 = _sdg1
|
||||
self.slicer_gate = _slicer_gate
|
||||
self.slicer_gate = _slicer_gate
|
||||
self.phase_shifter = _phase_shifter
|
||||
self.Id = 'SLAAR01-TSPL-EPL'
|
||||
self.name = 'lxt'
|
||||
self.Id = "SLAAR01-TSPL-EPL"
|
||||
self.name = "lxt"
|
||||
self.elog = None
|
||||
|
||||
def move_sdg(self,value):
|
||||
def move_sdg(self, value):
|
||||
self.sdg1.move(value)
|
||||
|
||||
def move(self,value,accuracy=None):
|
||||
def move(self, value, accuracy=None):
|
||||
self.sdg1.move(-value)
|
||||
self.slicer_gate.move(-value)
|
||||
self.phase_shifter.move(value,accuracy=accuracy)
|
||||
self.phase_shifter.move(value, accuracy=accuracy)
|
||||
|
||||
def set(self,value):
|
||||
def set(self, value):
|
||||
self.phase_shifter.set(value)
|
||||
self.sdg1.set(-value)
|
||||
|
||||
@@ -204,9 +216,9 @@ class Lxt(object):
|
||||
phase_shifter = self.phase_shifter.get()
|
||||
sdg1_delay = self.sdg1.get()
|
||||
|
||||
idx_pulse = (sdg1_delay+phase_shifter)/_OSCILLATOR_PERIOD
|
||||
idx_pulse = (sdg1_delay + phase_shifter) / _OSCILLATOR_PERIOD
|
||||
|
||||
delay = int(idx_pulse)*_OSCILLATOR_PERIOD - phase_shifter
|
||||
delay = int(idx_pulse) * _OSCILLATOR_PERIOD - phase_shifter
|
||||
return -delay
|
||||
|
||||
def set_target_value(self, value, hold=False):
|
||||
@@ -214,58 +226,60 @@ class Lxt(object):
|
||||
changer = lambda: self.move(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
def get_current_value(self):
|
||||
return self.get()
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self.set(value)
|
||||
|
||||
def __repr__(self):
|
||||
delay = niceTimeToStr(lxt.get())
|
||||
return "delay = %s"%(delay)
|
||||
return "delay = %s" % (delay)
|
||||
|
||||
|
||||
#lxt = Lxt()
|
||||
|
||||
|
||||
class eTiming:
|
||||
def __init__(self,Id):
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.name = 'Globi laser electronic timing (us)'
|
||||
self._eTimeSet = PV('SLAAR01-LTIM-PDLY:DELAY') # current laser timing number from Edwin's timing PV
|
||||
self._eTimeRBK = PV('SLAAR-LGEN:DLY_OFFS1') # readback on Edwin's timing PV
|
||||
self._moving = PV('SLAAR01-LTIM-PDLY:WAITING')
|
||||
self.name = "Globi laser electronic timing (us)"
|
||||
self._eTimeSet = PV("SLAAR01-LTIM-PDLY:DELAY") # current laser timing number from Edwin's timing PV
|
||||
self._eTimeRBK = PV("SLAAR-LGEN:DLY_OFFS1") # readback on Edwin's timing PV
|
||||
self._moving = PV("SLAAR01-LTIM-PDLY:WAITING")
|
||||
|
||||
def get_current_value(self):
|
||||
return self._eTimeRBK.get()*1e6 # convert from us to ps
|
||||
return self._eTimeRBK.get() * 1e6 # convert from us to ps
|
||||
|
||||
def wait_for_valid_value(self):
|
||||
tval = np.nan
|
||||
while not np.isfinite(tval):
|
||||
tval = self.get_current_value()
|
||||
return(tval)
|
||||
return tval
|
||||
|
||||
def move_and_wait(self,value,checktime=.01):
|
||||
def move_and_wait(self, value, checktime=0.01):
|
||||
self._eTimeSet.put(value)
|
||||
time.sleep(0.2)
|
||||
while self._moving.get()==0.0:
|
||||
while self._moving.get() == 0.0:
|
||||
time.sleep(checktime)
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self._eTimeSet.put(value)
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
def __str__(self):
|
||||
eTimingRBKStr = str(self.get_current_value())
|
||||
eTimingSetStr = self._eTimeSet.get(as_string=True)
|
||||
s = 'Globi laser electronic timing\n'
|
||||
s += '- electronic timing readback (ps): {}\n'.format(eTimingRBKStr)
|
||||
s += '- electronic timing setpoint (ps): {}'.format(eTimingSetStr)
|
||||
s = "Globi laser electronic timing\n"
|
||||
s += "- electronic timing readback (ps): {}\n".format(eTimingRBKStr)
|
||||
s += "- electronic timing setpoint (ps): {}".format(eTimingSetStr)
|
||||
return s
|
||||
|
||||
|
||||
|
||||
@@ -130,6 +130,7 @@ tim_tick = 7e-9
|
||||
|
||||
|
||||
class MasterEventSystem:
|
||||
|
||||
def __init__(self, pvname, name=None):
|
||||
self.name = name
|
||||
self.pvname = pvname
|
||||
@@ -187,23 +188,22 @@ class MasterEventSystem:
|
||||
Id = self._get_evtcode_Id(evtcode)
|
||||
return self._get_Id_period(Id) / 1000
|
||||
|
||||
def get_evt_code_status(self,codes=None):
|
||||
def get_evt_code_status(self, codes=None):
|
||||
if not codes:
|
||||
codes = sorted(eventcodes)
|
||||
if isinstance(codes,Number):
|
||||
if isinstance(codes, Number):
|
||||
codes = [codes]
|
||||
s = []
|
||||
for c in codes:
|
||||
s.append(f'{c:3d}: delay = {self.get_evtcode_delay(c)*1e6:9.3f} us; frequency: {self.get_evtcode_frequency(c):5.1f} Hz; Desc.: {self.get_evtcode_description(c)}')
|
||||
s.append(f"{c:3d}: delay = {self.get_evtcode_delay(c)*1e6:9.3f} us; frequency: {self.get_evtcode_frequency(c):5.1f} Hz; Desc.: {self.get_evtcode_description(c)}")
|
||||
return s
|
||||
|
||||
def status(self,codes=None):
|
||||
print('\n'.join(self.get_evt_code_status(codes)))
|
||||
|
||||
|
||||
def status(self, codes=None):
|
||||
print("\n".join(self.get_evt_code_status(codes)))
|
||||
|
||||
|
||||
class EvrPulser:
|
||||
|
||||
def __init__(self, pv_base, outputs=None, name=None):
|
||||
self.pv_base = pv_base
|
||||
self.name = name
|
||||
@@ -245,6 +245,7 @@ class EvrPulser:
|
||||
|
||||
|
||||
class EvrOutput:
|
||||
|
||||
def __init__(self, pv_base, name=None):
|
||||
self.pv_base = pv_base
|
||||
self.name = name
|
||||
@@ -280,9 +281,8 @@ class EvrOutput:
|
||||
|
||||
|
||||
class EventReceiver:
|
||||
def __init__(
|
||||
self, pvname, n_pulsers=24, n_output_front=8, n_output_rear=16, name=None
|
||||
):
|
||||
|
||||
def __init__(self, pvname, n_pulsers=24, n_output_front=8, n_output_rear=16, name=None):
|
||||
self.name = name
|
||||
self.pvname = pvname
|
||||
pulsers = []
|
||||
@@ -291,15 +291,14 @@ class EventReceiver:
|
||||
self.pulsers = tuple(pulsers)
|
||||
outputs = []
|
||||
for n in range(n_output_front):
|
||||
outputs.append(
|
||||
EvrOutput(f"{self.pvname}:FrontUnivOut{n}", name=f"output_front{n}")
|
||||
)
|
||||
outputs.append(EvrOutput(f"{self.pvname}:FrontUnivOut{n}", name=f"output_front{n}"))
|
||||
for to in outputs:
|
||||
to._pulsers = self.pulsers
|
||||
self.outputs = outputs
|
||||
|
||||
|
||||
class CTA_sequencer:
|
||||
|
||||
def __init__(self, Id, name=None, master_frequency=100):
|
||||
self._cta = CtaLib(Id)
|
||||
self.sequence_local = {}
|
||||
@@ -332,7 +331,7 @@ class CTA_sequencer:
|
||||
config={
|
||||
"mode": self._cta.StartMode(mode),
|
||||
"modulo": divisor,
|
||||
"offset": offset,
|
||||
"offset": offset
|
||||
}
|
||||
)
|
||||
|
||||
@@ -370,3 +369,6 @@ class CTA_sequencer:
|
||||
|
||||
def stop(self):
|
||||
self._cta.stop()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -83,6 +83,7 @@ class Storage(object):
|
||||
|
||||
|
||||
class Pockels_trigger(PV):
|
||||
|
||||
def __init__(self, pv_get, pv_set, pv_offset_get=None):
|
||||
pvname = pv_get
|
||||
PV.__init__(self, pvname)
|
||||
@@ -96,11 +97,7 @@ class Pockels_trigger(PV):
|
||||
return self._storage.value
|
||||
|
||||
def get_dial(self):
|
||||
return (
|
||||
np.round(super().get() * 1e-6, 9)
|
||||
+ self._pv_offset_get.get() * 1e-9
|
||||
- 7.41e-9
|
||||
)
|
||||
return np.round(super().get() * 1e-6, 9) + self._pv_offset_get.get() * 1e-9 - 7.41e-9
|
||||
|
||||
def get(self):
|
||||
""" convert time to sec """
|
||||
@@ -131,9 +128,7 @@ _OSCILLATOR_PERIOD = 1 / 71.368704e6
|
||||
class Phase_shifter(PV):
|
||||
""" this class is needed to store the offset in files and read in ps """
|
||||
|
||||
def __init__(
|
||||
self, pv_basename="SLAAR02-TSPL-EPL", dial_max=14.0056e-9, precision=100e-15
|
||||
):
|
||||
def __init__(self, pv_basename="SLAAR02-TSPL-EPL", dial_max=14.0056e-9, precision=100e-15):
|
||||
pvname = pv_basename + ":CURR_DELTA_T"
|
||||
PV.__init__(self, pvname)
|
||||
self._filename = os.path.join(_basefolder, pvname)
|
||||
@@ -186,17 +181,9 @@ class Phase_shifter(PV):
|
||||
return "Phase Shifter: user,dial = %s , %s" % (user, dial)
|
||||
|
||||
|
||||
_slicer_gate = Pockels_trigger(
|
||||
"SLAAR-LTIM02-EVR0:Pul3-Delay-RB",
|
||||
"SLAAR-LTIM02-EVR0:Pul3_NEW_DELAY",
|
||||
pv_offset_get="SLAAR-LTIM02-EVR0:UnivDlyModule1-Delay1-RB",
|
||||
)
|
||||
_slicer_gate = Pockels_trigger("SLAAR-LTIM02-EVR0:Pul3-Delay-RB", "SLAAR-LTIM02-EVR0:Pul3_NEW_DELAY", pv_offset_get="SLAAR-LTIM02-EVR0:UnivDlyModule1-Delay1-RB",)
|
||||
|
||||
_sdg1 = Pockels_trigger(
|
||||
"SLAAR-LTIM02-EVR0:Pul2-Delay-RB",
|
||||
"SLAAR-LTIM02-EVR0:Pul2_NEW_DELAY",
|
||||
pv_offset_get="SLAAR-LTIM02-EVR0:UnivDlyModule1-Delay0-RB",
|
||||
)
|
||||
_sdg1 = Pockels_trigger("SLAAR-LTIM02-EVR0:Pul2-Delay-RB", "SLAAR-LTIM02-EVR0:Pul2_NEW_DELAY", pv_offset_get="SLAAR-LTIM02-EVR0:UnivDlyModule1-Delay0-RB",)
|
||||
|
||||
_phase_shifter = Phase_shifter("SLAAR02-TSPL-EPL")
|
||||
|
||||
@@ -205,6 +192,7 @@ _POCKELS_CELL_RESOLUTION = 7e-9
|
||||
|
||||
|
||||
class Lxt(object):
|
||||
|
||||
def __init__(self, accuracy_poly=[100e-15, 1e-7]):
|
||||
self.sdg1 = _sdg1
|
||||
self.slicer_gate = _slicer_gate
|
||||
@@ -257,3 +245,6 @@ class Lxt(object):
|
||||
|
||||
|
||||
lxt = Lxt()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -6,6 +6,7 @@ from ...general.delay_stage import DelayStage
|
||||
|
||||
|
||||
class Palm:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
|
||||
@@ -6,6 +6,7 @@ from ...general.delay_stage import DelayStage
|
||||
|
||||
|
||||
class Psen:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
|
||||
@@ -33,3 +33,6 @@ def plotTrace(fina="./scope2_testdata_2017-02-21/C2Trace00003txt"):
|
||||
ax.plot(crossers[0], crossers[1], "xr")
|
||||
ax.set_xlabel("Time / s")
|
||||
ax.set_ylabel("Amplitude / V")
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -5,6 +5,7 @@ from subprocess import Popen, PIPE, STDOUT
|
||||
|
||||
|
||||
class ScreenPanel:
|
||||
|
||||
def __init__(self, name=None):
|
||||
self.name = name
|
||||
self._proc = None
|
||||
@@ -12,12 +13,7 @@ class ScreenPanel:
|
||||
@property
|
||||
def proc(self):
|
||||
if not self._proc:
|
||||
if (
|
||||
input(
|
||||
"No screenpanel running, would you like to start now? (y/n)\n"
|
||||
).strip()
|
||||
== "y"
|
||||
):
|
||||
if input("No screenpanel running, would you like to start now? (y/n)\n").strip() == "y":
|
||||
self.start()
|
||||
return self._proc
|
||||
|
||||
@@ -26,12 +22,7 @@ class ScreenPanel:
|
||||
print(f"Sreenpanel {self.name} is already running")
|
||||
else:
|
||||
# self.proc = subprocess.Popen(["screen_panel","-console"],stdout=subprocess.PIPE)
|
||||
self._proc = Popen(
|
||||
["bash", "screen_panel", "-console", "-persist"],
|
||||
stdin=PIPE,
|
||||
stdout=PIPE,
|
||||
preexec_fn=os.setsid,
|
||||
)
|
||||
self._proc = Popen(["bash", "screen_panel", "-console", "-persist"], stdin=PIPE, stdout=PIPE, preexec_fn=os.setsid,)
|
||||
|
||||
def quit(self):
|
||||
os.killpg(self.proc.pid, signal.SIGTERM)
|
||||
@@ -40,3 +31,6 @@ class ScreenPanel:
|
||||
def set_camera(self, camera_name):
|
||||
self.proc.stdin.write(("cam " + camera_name + "\n").encode())
|
||||
self.proc.stdin.flush()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -4,53 +4,52 @@ from ..general.detectors import FeDigitizer
|
||||
|
||||
|
||||
class GasDetector:
|
||||
|
||||
def __init__(self):
|
||||
pass
|
||||
|
||||
|
||||
class SolidTargetDetectorPBPS:
|
||||
def __init__(self, Id, VME_crate=None, link=None,
|
||||
ch_up=12, ch_down=13, ch_left=15, ch_right=14,
|
||||
elog=None, z_undulator=None, description=None):
|
||||
|
||||
def __init__(self, Id, VME_crate=None, link=None, ch_up=12, ch_down=13, ch_left=15, ch_right=14, elog=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.x_diode = Motor(Id + ':MOTOR_X1',elog=elog)
|
||||
self.y_diode = Motor(Id + ':MOTOR_Y1',elog=elog)
|
||||
self.y_target = Motor(Id + ':MOTOR_PROBE',elog=elog)
|
||||
self.target = EnumWrapper(Id + ':PROBE_SP',elog=elog)
|
||||
self.x_diode = Motor(Id + ":MOTOR_X1", elog=elog)
|
||||
self.y_diode = Motor(Id + ":MOTOR_Y1", elog=elog)
|
||||
self.y_target = Motor(Id + ":MOTOR_PROBE", elog=elog)
|
||||
self.target = EnumWrapper(Id + ":PROBE_SP", elog=elog)
|
||||
if VME_crate:
|
||||
self.diode_up = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_up))
|
||||
self.diode_down = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_down))
|
||||
self.diode_left = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_left))
|
||||
self.diode_right = FeDigitizer('%s:Lnk%dCh%d'%(VME_crate,link,ch_right))
|
||||
self.diode_up = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_up))
|
||||
self.diode_down = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_down))
|
||||
self.diode_left = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_left))
|
||||
self.diode_right = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_right))
|
||||
|
||||
def __repr__(self):
|
||||
s = "**Intensity monitor**\n\n"
|
||||
|
||||
s+= "Target: " + (self.target.get_name()) + "\n\n"
|
||||
s += "Target: " + (self.target.get_name()) + "\n\n"
|
||||
|
||||
s+= "**Bias voltage**\n"
|
||||
s+= " - Diode up: %.4f\n" %(self.diode_up.get_bias())
|
||||
s+= " - Diode down: %.4f\n" %(self.diode_down.get_bias())
|
||||
s+= " - Diode left: %.4f\n" %(self.diode_left.get_bias())
|
||||
s+= " - Diode right: %.4f\n" %(self.diode_right.get_bias())
|
||||
s+= "\n"
|
||||
s += "**Bias voltage**\n"
|
||||
s += " - Diode up: %.4f\n" % (self.diode_up.get_bias())
|
||||
s += " - Diode down: %.4f\n" % (self.diode_down.get_bias())
|
||||
s += " - Diode left: %.4f\n" % (self.diode_left.get_bias())
|
||||
s += " - Diode right: %.4f\n" % (self.diode_right.get_bias())
|
||||
s += "\n"
|
||||
|
||||
s+= "**Gain**\n"
|
||||
s+= " - Diode up: %i\n" %(self.diode_up.gain.get())
|
||||
s+= " - Diode down: %i\n" %(self.diode_down.gain.get())
|
||||
s+= " - Diode left: %i\n" %(self.diode_left.gain.get())
|
||||
s+= " - Diode right: %i\n" %(self.diode_right.gain.get())
|
||||
s += "**Gain**\n"
|
||||
s += " - Diode up: %i\n" % (self.diode_up.gain.get())
|
||||
s += " - Diode down: %i\n" % (self.diode_down.gain.get())
|
||||
s += " - Diode left: %i\n" % (self.diode_left.gain.get())
|
||||
s += " - Diode right: %i\n" % (self.diode_right.gain.get())
|
||||
return s
|
||||
|
||||
|
||||
def set_gains(self,value):
|
||||
def set_gains(self, value):
|
||||
try:
|
||||
self.diode_up.gain.set(value)
|
||||
self.diode_down.gain.set(value)
|
||||
self.diode_left.gain.set(value)
|
||||
self.diode_right.gain.set(value)
|
||||
except:
|
||||
print('No diodes configured, can not change any gain!')
|
||||
print("No diodes configured, can not change any gain!")
|
||||
|
||||
def get_available_gains(self):
|
||||
try:
|
||||
@@ -58,23 +57,21 @@ class SolidTargetDetectorPBPS:
|
||||
nd = self.diode_down.gain.names
|
||||
nl = self.diode_left.gain.names
|
||||
nr = self.diode_right.gain.names
|
||||
assert nu==nd==nl==nr , 'NB: the gain options of the four diodes are not equal!!!'
|
||||
assert nu == nd == nl == nr, "NB: the gain options of the four diodes are not equal!!!"
|
||||
return nu
|
||||
except:
|
||||
print('No diodes configured, can not change any gain!')
|
||||
print("No diodes configured, can not change any gain!")
|
||||
|
||||
def get_gains(self):
|
||||
try:
|
||||
gains = dict()
|
||||
gains['up'] = (self.diode_up.gain.get_name(),self.diode_up.gain.get())
|
||||
gains['down'] = (self.diode_down.gain.get_name(),self.diode_down.gain.get())
|
||||
gains['left'] = (self.diode_left.gain.get_name(),self.diode_left.gain.get())
|
||||
gains['right'] = (self.diode_right.gain.get_name(),self.diode_right.gain.get())
|
||||
gains["up"] = (self.diode_up.gain.get_name(), self.diode_up.gain.get())
|
||||
gains["down"] = (self.diode_down.gain.get_name(), self.diode_down.gain.get())
|
||||
gains["left"] = (self.diode_left.gain.get_name(), self.diode_left.gain.get())
|
||||
gains["right"] = (self.diode_right.gain.get_name(), self.diode_right.gain.get())
|
||||
return gains
|
||||
except:
|
||||
print('No diodes configured, can not change any gain!')
|
||||
|
||||
|
||||
print("No diodes configured, can not change any gain!")
|
||||
|
||||
#SAROP21-CVME-PBPS:Lnk10Ch15-WD-gain
|
||||
|
||||
|
||||
@@ -8,30 +8,16 @@ from slic.core.adjustable import PVEnumAdjustable
|
||||
from slic.utils.eco_components.aliases import Alias, append_object_to_object
|
||||
|
||||
|
||||
|
||||
|
||||
class GasDetector:
|
||||
|
||||
def __init__(self):
|
||||
pass
|
||||
|
||||
|
||||
|
||||
class SolidTargetDetectorPBPS_new:
|
||||
def __init__(
|
||||
self,
|
||||
pvname,
|
||||
VME_crate=None,
|
||||
link=None,
|
||||
channels = {},
|
||||
ch_up=12,
|
||||
ch_down=13,
|
||||
ch_left=15,
|
||||
ch_right=14,
|
||||
elog=None,
|
||||
name=None,
|
||||
calc=None,
|
||||
calc_calib={},
|
||||
|
||||
def __init__(
|
||||
self, pvname, VME_crate=None, link=None, channels={}, ch_up=12, ch_down=13, ch_left=15, ch_right=14, elog=None, name=None, calc=None, calc_calib={},
|
||||
):
|
||||
self.name = name
|
||||
self.pvname = pvname
|
||||
@@ -46,17 +32,16 @@ class SolidTargetDetectorPBPS_new:
|
||||
self.diode_left = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_left))
|
||||
self.diode_right = FeDigitizer("%s:Lnk%dCh%d" % (VME_crate, link, ch_right))
|
||||
|
||||
|
||||
if channels:
|
||||
append_object_to_object(self, PvDataStream, channels['up'], name="signal_up")
|
||||
append_object_to_object(self, PvDataStream, channels['down'], name="signal_down")
|
||||
append_object_to_object(self, PvDataStream, channels['left'], name="signal_left")
|
||||
append_object_to_object(self, PvDataStream, channels['right'], name="signal_right")
|
||||
append_object_to_object(self, PvDataStream, channels["up"], name="signal_up")
|
||||
append_object_to_object(self, PvDataStream, channels["down"], name="signal_down")
|
||||
append_object_to_object(self, PvDataStream, channels["left"], name="signal_left")
|
||||
append_object_to_object(self, PvDataStream, channels["right"], name="signal_right")
|
||||
|
||||
if calc:
|
||||
append_object_to_object(self, PvDataStream, calc['itot'], name="intensity")
|
||||
append_object_to_object(self, PvDataStream, calc['xpos'], name="xpos")
|
||||
append_object_to_object(self, PvDataStream, calc['ypos'], name="ypos")
|
||||
append_object_to_object(self, PvDataStream, calc["itot"], name="intensity")
|
||||
append_object_to_object(self, PvDataStream, calc["xpos"], name="xpos")
|
||||
append_object_to_object(self, PvDataStream, calc["ypos"], name="ypos")
|
||||
|
||||
def get_calibration_values(self, seconds=5):
|
||||
self.x_diodes.set_target_value(0).wait()
|
||||
@@ -66,68 +51,62 @@ class SolidTargetDetectorPBPS_new:
|
||||
data = [aq.wait() for aq in aqs]
|
||||
mean = [np.mean(td) for td in data]
|
||||
std = [np.std(td) for td in data]
|
||||
norm_diodes = [1/tm/4 for tm in mean]
|
||||
norm_diodes = [1 / tm / 4 for tm in mean]
|
||||
return norm_diodes
|
||||
|
||||
def set_calibration_values(self, norm_diodes):
|
||||
#this is now only for bernina when using the ioxos from sla
|
||||
channels = ['SLAAR21-LTIM01-EVR0:CALCI.INPG','SLAAR21-LTIM01-EVR0:CALCI.INPH','SLAAR21-LTIM01-EVR0:CALCI.INPF','SLAAR21-LTIM01-EVR0:CALCI.INPE']
|
||||
for tc,tv in zip(channels,norm_diodes):
|
||||
PV(tc).put(bytes(str(tv),'utf8'))
|
||||
channels = ['SLAAR21-LTIM01-EVR0:CALCX.INPE','SLAAR21-LTIM01-EVR0:CALCX.INPF']
|
||||
for tc,tv in zip(channels,norm_diodes[2:4]):
|
||||
PV(tc).put(bytes(str(tv),'utf8'))
|
||||
channels = ['SLAAR21-LTIM01-EVR0:CALCY.INPE','SLAAR21-LTIM01-EVR0:CALCY.INPF']
|
||||
for tc,tv in zip(channels,norm_diodes[0:2]):
|
||||
PV(tc).put(bytes(str(tv),'utf8'))
|
||||
channels = ["SLAAR21-LTIM01-EVR0:CALCI.INPG", "SLAAR21-LTIM01-EVR0:CALCI.INPH", "SLAAR21-LTIM01-EVR0:CALCI.INPF", "SLAAR21-LTIM01-EVR0:CALCI.INPE"]
|
||||
for tc, tv in zip(channels, norm_diodes):
|
||||
PV(tc).put(bytes(str(tv), "utf8"))
|
||||
channels = ["SLAAR21-LTIM01-EVR0:CALCX.INPE", "SLAAR21-LTIM01-EVR0:CALCX.INPF"]
|
||||
for tc, tv in zip(channels, norm_diodes[2:4]):
|
||||
PV(tc).put(bytes(str(tv), "utf8"))
|
||||
channels = ["SLAAR21-LTIM01-EVR0:CALCY.INPE", "SLAAR21-LTIM01-EVR0:CALCY.INPF"]
|
||||
for tc, tv in zip(channels, norm_diodes[0:2]):
|
||||
PV(tc).put(bytes(str(tv), "utf8"))
|
||||
|
||||
def get_calibration_values_position(self, calib_intensities,seconds=5, motion_range=.2):
|
||||
self.x_diodes.set_limits(-motion_range/2-.1,+motion_range/2+.1)
|
||||
self.y_diodes.set_limits(-motion_range/2-.1,+motion_range/2+.1)
|
||||
def get_calibration_values_position(self, calib_intensities, seconds=5, motion_range=0.2):
|
||||
self.x_diodes.set_limits(-motion_range / 2 - 0.1, +motion_range / 2 + 0.1)
|
||||
self.y_diodes.set_limits(-motion_range / 2 - 0.1, +motion_range / 2 + 0.1)
|
||||
self.x_diodes.set_target_value(0).wait()
|
||||
self.y_diodes.set_target_value(0).wait()
|
||||
raw = []
|
||||
for pos in [motion_range/2, -motion_range/2]:
|
||||
for pos in [motion_range / 2, -motion_range / 2]:
|
||||
self.x_diodes.set_target_value(pos).wait()
|
||||
aqs = [ts.acquire(seconds=seconds) for ts in [self.signal_left, self.signal_right]]
|
||||
vals = [np.mean(aq.wait())*calib for aq,calib in zip(aqs,calib_intensities[0:2])]
|
||||
raw.append((vals[0]-vals[1])/(vals[0]+vals[1]))
|
||||
grad = motion_range/np.diff(raw)[0]
|
||||
vals = [np.mean(aq.wait()) * calib for aq, calib in zip(aqs, calib_intensities[0:2])]
|
||||
raw.append((vals[0] - vals[1]) / (vals[0] + vals[1]))
|
||||
grad = motion_range / np.diff(raw)[0]
|
||||
# xcalib = [np.diff(calib_intensities[0:2])[0]/np.sum(calib_intensities[0:2]), grad]
|
||||
xcalib = [0, grad]
|
||||
self.x_diodes.set_target_value(0).wait()
|
||||
raw = []
|
||||
for pos in [motion_range/2, -motion_range/2]:
|
||||
for pos in [motion_range / 2, -motion_range / 2]:
|
||||
self.y_diodes.set_target_value(pos).wait()
|
||||
aqs = [ts.acquire(seconds=seconds) for ts in [self.signal_up, self.signal_down]]
|
||||
vals = [np.mean(aq.wait())*calib for aq,calib in zip(aqs,calib_intensities[2:4])]
|
||||
raw.append((vals[0]-vals[1])/(vals[0]+vals[1]))
|
||||
grad = motion_range/np.diff(raw)[0]
|
||||
vals = [np.mean(aq.wait()) * calib for aq, calib in zip(aqs, calib_intensities[2:4])]
|
||||
raw.append((vals[0] - vals[1]) / (vals[0] + vals[1]))
|
||||
grad = motion_range / np.diff(raw)[0]
|
||||
# ycalib = [np.diff(calib_intensities[2:4])[0]/np.sum(calib_intensities[2:4]), grad]
|
||||
ycalib = [0, grad]
|
||||
self.y_diodes.set_target_value(0).wait()
|
||||
return xcalib,ycalib
|
||||
return xcalib, ycalib
|
||||
|
||||
def set_calibration_values_position(self, xcalib, ycalib):
|
||||
channels = ['SLAAR21-LTIM01-EVR0:CALCX.INPJ','SLAAR21-LTIM01-EVR0:CALCX.INPI']
|
||||
channels = ["SLAAR21-LTIM01-EVR0:CALCX.INPJ", "SLAAR21-LTIM01-EVR0:CALCX.INPI"]
|
||||
# txcalib = [-1*xcalib[0],-1*xcalib[1]]
|
||||
for tc,tv in zip(channels,xcalib):
|
||||
PV(tc).put(bytes(str(tv),'utf8'))
|
||||
channels = ['SLAAR21-LTIM01-EVR0:CALCY.INPJ','SLAAR21-LTIM01-EVR0:CALCY.INPI']
|
||||
for tc,tv in zip(channels,ycalib):
|
||||
PV(tc).put(bytes(str(tv),'utf8'))
|
||||
for tc, tv in zip(channels, xcalib):
|
||||
PV(tc).put(bytes(str(tv), "utf8"))
|
||||
channels = ["SLAAR21-LTIM01-EVR0:CALCY.INPJ", "SLAAR21-LTIM01-EVR0:CALCY.INPI"]
|
||||
for tc, tv in zip(channels, ycalib):
|
||||
PV(tc).put(bytes(str(tv), "utf8"))
|
||||
|
||||
|
||||
def calibrate(self,seconds=5):
|
||||
def calibrate(self, seconds=5):
|
||||
c = self.get_calibration_values(seconds=seconds)
|
||||
self.set_calibration_values(c)
|
||||
xc,yc = self.get_calibration_values_position(c,seconds=seconds)
|
||||
self.set_calibration_values_position(xc,yc)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
xc, yc = self.get_calibration_values_position(c, seconds=seconds)
|
||||
self.set_calibration_values_position(xc, yc)
|
||||
|
||||
def __repr__(self):
|
||||
s = f"**Intensity monitor {self.name}**\n\n"
|
||||
@@ -166,9 +145,7 @@ class SolidTargetDetectorPBPS_new:
|
||||
nd = self.diode_down.gain.names
|
||||
nl = self.diode_left.gain.names
|
||||
nr = self.diode_right.gain.names
|
||||
assert (
|
||||
nu == nd == nl == nr
|
||||
), "NB: the gain options of the four diodes are not equal!!!"
|
||||
assert nu == nd == nl == nr, "NB: the gain options of the four diodes are not equal!!!"
|
||||
return nu
|
||||
except:
|
||||
print("No diodes configured, can not change any gain!")
|
||||
@@ -194,18 +171,12 @@ class SolidTargetDetectorPBPS_new:
|
||||
print("No diodes configured, can not change any gain!")
|
||||
|
||||
# SAROP21-CVME-PBPS:Lnk10Ch15-WD-gain
|
||||
|
||||
|
||||
class SolidTargetDetectorPBPS:
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
Id,
|
||||
VME_crate=None,
|
||||
link=None,
|
||||
ch_up=12,
|
||||
ch_down=13,
|
||||
ch_left=15,
|
||||
ch_right=14,
|
||||
elog=None,
|
||||
name=None,
|
||||
self, Id, VME_crate=None, link=None, ch_up=12, ch_down=13, ch_left=15, ch_right=14, elog=None, name=None,
|
||||
):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -263,9 +234,7 @@ class SolidTargetDetectorPBPS:
|
||||
nd = self.diode_down.gain.names
|
||||
nl = self.diode_left.gain.names
|
||||
nr = self.diode_right.gain.names
|
||||
assert (
|
||||
nu == nd == nl == nr
|
||||
), "NB: the gain options of the four diodes are not equal!!!"
|
||||
assert nu == nd == nl == nr, "NB: the gain options of the four diodes are not equal!!!"
|
||||
return nu
|
||||
except:
|
||||
print("No diodes configured, can not change any gain!")
|
||||
|
||||
@@ -2,39 +2,41 @@ from epics import PV
|
||||
|
||||
from slic.devices.general.motor import Motor
|
||||
from ..general.detectors import CameraCA, CameraBS
|
||||
|
||||
#from ..general.epics_wrappers import EnumSelector
|
||||
from slic.utils.eco_epics.utilities_epics import EnumWrapper
|
||||
|
||||
|
||||
class Pprm:
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.targetY = Motor(Id + ':MOTOR_PROBE')
|
||||
self.targetY = Motor(Id + ":MOTOR_PROBE")
|
||||
self.cam = CameraCA(Id)
|
||||
self._led = PV(self.Id + ':LED')
|
||||
self.target = EnumWrapper(self.Id + ':PROBE_SP')
|
||||
self._led = PV(self.Id + ":LED")
|
||||
self.target = EnumWrapper(self.Id + ":PROBE_SP")
|
||||
|
||||
def illuminate(self,value=None):
|
||||
def illuminate(self, value=None):
|
||||
if value:
|
||||
self._led.put(value)
|
||||
else:
|
||||
self._led.put(
|
||||
not self.get_illumination_state())
|
||||
self._led.put(not self.get_illumination_state())
|
||||
|
||||
def get_illumination_state(self):
|
||||
return bool(self._led.get())
|
||||
|
||||
def __repr__(self):
|
||||
s = "**Profile Monitor**\n"
|
||||
s+= "Target: %s" %(self.target.get_name())
|
||||
s += "Target: %s" % (self.target.get_name())
|
||||
return s
|
||||
|
||||
|
||||
class Bernina_XEYE:
|
||||
def __init__(self,Id,bshost=None,bsport=None):
|
||||
|
||||
def __init__(self, Id, bshost=None, bsport=None):
|
||||
self.Id = Id
|
||||
try:
|
||||
self.zoom = Motor('SARES20-EXP:MOT_NAV_Z.VAL')
|
||||
self.zoom = Motor("SARES20-EXP:MOT_NAV_Z.VAL")
|
||||
except:
|
||||
print("X-Ray eye zoom motor not found")
|
||||
pass
|
||||
@@ -45,10 +47,11 @@ class Bernina_XEYE:
|
||||
pass
|
||||
|
||||
if bshost:
|
||||
self.camBS = CameraBS(host=bshost,port=bsport)
|
||||
# self._led = PV(self.Id + ':LED')
|
||||
self.camBS = CameraBS(host=bshost, port=bsport)
|
||||
|
||||
|
||||
# self._led = PV(self.Id + ':LED')
|
||||
|
||||
|
||||
# def illuminate(self,value=None):
|
||||
# if value:
|
||||
|
||||
@@ -14,6 +14,7 @@ def addMotorToSelf(self, Id=None, name=None):
|
||||
|
||||
|
||||
class Pprm:
|
||||
|
||||
def __init__(self, Id, name=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -40,9 +41,8 @@ class Pprm:
|
||||
|
||||
|
||||
class Bernina_XEYE:
|
||||
def __init__(
|
||||
self, camera_pv=None, zoomstage_pv=None, bshost=None, bsport=None, name=None
|
||||
):
|
||||
|
||||
def __init__(self, camera_pv=None, zoomstage_pv=None, bshost=None, bsport=None, name=None):
|
||||
self.alias = Alias(name)
|
||||
self.name = name
|
||||
if zoomstage_pv:
|
||||
|
||||
@@ -1,45 +1,48 @@
|
||||
from slic.devices.general.motor import Motor
|
||||
# from ..devices_general.smaract import SmarActRecord
|
||||
# from epics import PV
|
||||
|
||||
#from ..devices_general.smaract import SmarActRecord
|
||||
#from epics import PV
|
||||
from ..general.delay_stage import DelayStage
|
||||
# from ..devices_general.adjustable import
|
||||
|
||||
#from ..devices_general.adjustable import
|
||||
from slic.utils.eco_components.aliases import Alias, append_object_to_object
|
||||
from psen_processing import PsenProcessingClient
|
||||
from ..loptics.bernina_experiment import DelayTime
|
||||
from cam_server import PipelineClient
|
||||
|
||||
|
||||
|
||||
class SpectralEncoder:
|
||||
def __init__(self, pvname, name=None, reduction_client_address="http://sf-daqsync-02:12002/",delay_stages={'spect_tt':"SLAAR21-LMOT-M553:MOT","retroreflector":"SLAAR21-LMOT-M561:MOT"}):
|
||||
|
||||
def __init__(self, pvname, name=None, reduction_client_address="http://sf-daqsync-02:12002/", delay_stages={"spect_tt": "SLAAR21-LMOT-M553:MOT", "retroreflector": "SLAAR21-LMOT-M561:MOT"}):
|
||||
self.pvname = pvname
|
||||
self.name=name
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
append_object_to_object(self, Motor, pvname+":MOTOR_X1", name='x_target')
|
||||
append_object_to_object(self, Motor, pvname+":MOTOR_Y1", name='y_target')
|
||||
append_object_to_object(self, Motor, pvname + ":MOTOR_X1", name="x_target")
|
||||
append_object_to_object(self, Motor, pvname + ":MOTOR_Y1", name="y_target")
|
||||
if delay_stages:
|
||||
for key,pv in delay_stages.items():
|
||||
tname = 'delay_'+key+'_stg'
|
||||
for key, pv in delay_stages.items():
|
||||
tname = "delay_" + key + "_stg"
|
||||
append_object_to_object(self, Motor, pv, name=tname)
|
||||
append_object_to_object(self, DelayTime, self.__dict__[tname], name='delay_'+key)
|
||||
append_object_to_object(self, DelayTime, self.__dict__[tname], name="delay_" + key)
|
||||
|
||||
# self.delay = Motor(self.Id + "-M424:MOT")
|
||||
# self.delayTime = DelayStage(self.delay)
|
||||
self.data_reduction_client = PsenProcessingClient(address=reduction_client_address)
|
||||
#self.delay = Motor(self.Id + "-M424:MOT")
|
||||
#self.delayTime = DelayStage(self.delay)
|
||||
self.data_reduction_client = PsenProcessingClient(address=reduction_client_address)
|
||||
|
||||
|
||||
@property
|
||||
def roi(self):
|
||||
return self.data_reduction_client.get_roi_signal()
|
||||
|
||||
@roi.setter
|
||||
def roi(self,values):
|
||||
def roi(self, values):
|
||||
self.data_reduction_client.set_roi_signal(values)
|
||||
|
||||
|
||||
@property
|
||||
def roi_background(self):
|
||||
return self.data_reduction_client.get_roi_background()
|
||||
|
||||
@roi_background.setter
|
||||
def roi_background(self,values):
|
||||
def roi_background(self, values):
|
||||
self.data_reduction_client.set_roi_background(values)
|
||||
|
||||
def __repr__(self):
|
||||
@@ -49,65 +52,66 @@ class SpectralEncoder:
|
||||
s.append(f"Data reduction is on")
|
||||
s.append(f" roi {self.roi}")
|
||||
s.append(f" roi_background {self.roi_background}")
|
||||
return '\n'.join(s)
|
||||
return "\n".join(s)
|
||||
|
||||
|
||||
class SpatialEncoder:
|
||||
def __init__(self, name=None, reduction_client_address="http://sf-daqsync-02:12003/",delay_stages={'spatial_tt':"SLAAR21-LMOT-M522:MOTOR_1"},pipeline_id='SARES20-CAMS142-M4_psen_db1'):
|
||||
self.name=name
|
||||
self.alias = Alias(name)
|
||||
# append_object_to_object(self,Motor,pvname+":MOTOR_X1",name='x_target')
|
||||
# append_object_to_object(self,Motor,pvname+":MOTOR_Y1",name='y_target')
|
||||
if delay_stages:
|
||||
for key,pv in delay_stages.items():
|
||||
tname = 'delay_'+key+'_stg'
|
||||
append_object_to_object(self,Motor,pv,name=tname)
|
||||
append_object_to_object(self,DelayTime,self.__dict__[tname],name='delay_'+key)
|
||||
|
||||
# self.delay = Motor(self.Id + "-M424:MOT")
|
||||
# self.delayTime = DelayStage(self.delay)
|
||||
# self.data_reduction_client = PsenProcessingClient(address=reduction_client_address)
|
||||
def __init__(self, name=None, reduction_client_address="http://sf-daqsync-02:12003/", delay_stages={"spatial_tt": "SLAAR21-LMOT-M522:MOTOR_1"}, pipeline_id="SARES20-CAMS142-M4_psen_db1"):
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
#append_object_to_object(self,Motor,pvname+":MOTOR_X1",name='x_target')
|
||||
#append_object_to_object(self,Motor,pvname+":MOTOR_Y1",name='y_target')
|
||||
if delay_stages:
|
||||
for key, pv in delay_stages.items():
|
||||
tname = "delay_" + key + "_stg"
|
||||
append_object_to_object(self, Motor, pv, name=tname)
|
||||
append_object_to_object(self, DelayTime, self.__dict__[tname], name="delay_" + key)
|
||||
|
||||
#self.delay = Motor(self.Id + "-M424:MOT")
|
||||
#self.delayTime = DelayStage(self.delay)
|
||||
#self.data_reduction_client = PsenProcessingClient(address=reduction_client_address)
|
||||
self._camera_server_client = PipelineClient()
|
||||
self._camera_server_pipeline_id = pipeline_id
|
||||
|
||||
#@property
|
||||
#def roi(self):
|
||||
# return self.data_reduction_client.get_roi_signal()
|
||||
#@roi.setter
|
||||
#def roi(self,values):
|
||||
# self.data_reduction_client.set_roi_signal(values)
|
||||
|
||||
|
||||
# @property
|
||||
# def roi(self):
|
||||
# return self.data_reduction_client.get_roi_signal()
|
||||
# @roi.setter
|
||||
# def roi(self,values):
|
||||
# self.data_reduction_client.set_roi_signal(values)
|
||||
|
||||
# @property
|
||||
# def roi_background(self):
|
||||
# return self.data_reduction_client.get_roi_background()
|
||||
# @roi_background.setter
|
||||
# def roi_background(self,values):
|
||||
# self.data_reduction_client.set_roi_background(values)
|
||||
#@property
|
||||
#def roi_background(self):
|
||||
# return self.data_reduction_client.get_roi_background()
|
||||
#@roi_background.setter
|
||||
#def roi_background(self,values):
|
||||
# self.data_reduction_client.set_roi_background(values)
|
||||
|
||||
@property
|
||||
def roi(self):
|
||||
return self._camera_server_client.get_instance_config(self._camera_server_pipeline_id)['roi_signal']
|
||||
return self._camera_server_client.get_instance_config(self._camera_server_pipeline_id)["roi_signal"]
|
||||
|
||||
@roi.setter
|
||||
def roi(self,values):
|
||||
self._camera_server_client.set_instance_config(self._camera_server_pipeline_id,{'roi_signal':values})
|
||||
|
||||
def roi(self, values):
|
||||
self._camera_server_client.set_instance_config(self._camera_server_pipeline_id, {"roi_signal": values})
|
||||
|
||||
@property
|
||||
def roi_background(self):
|
||||
return self._camera_server_client.get_instance_config(self._camera_server_pipeline_id)['roi_background']
|
||||
@roi_background.setter
|
||||
def roi_background(self,values):
|
||||
self._camera_server_client.set_instance_config(self._camera_server_pipeline_id,{'roi_background':values})
|
||||
return self._camera_server_client.get_instance_config(self._camera_server_pipeline_id)["roi_background"]
|
||||
|
||||
@roi_background.setter
|
||||
def roi_background(self, values):
|
||||
self._camera_server_client.set_instance_config(self._camera_server_pipeline_id, {"roi_background": values})
|
||||
|
||||
def __repr__(self):
|
||||
s = [f"Status {self.name}"]
|
||||
# s.append(str(self.x_target))
|
||||
# s.append(str(self.y_target))
|
||||
#s.append(str(self.x_target))
|
||||
#s.append(str(self.y_target))
|
||||
s.append(f"Data reduction is on")
|
||||
s.append(f" roi {self.roi}")
|
||||
s.append(f" roi_background {self.roi_background}")
|
||||
return '\n'.join(s)
|
||||
return "\n".join(s)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -6,6 +6,7 @@ from ...general.delay_stage import DelayStage
|
||||
|
||||
|
||||
class palm:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
@@ -29,6 +30,7 @@ class palm:
|
||||
|
||||
|
||||
class eo:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
|
||||
@@ -6,23 +6,22 @@ from ...general.delay_stage import DelayStage
|
||||
|
||||
|
||||
class psen:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
|
||||
self.delay = Motor(self.Id + '-M424:MOT')
|
||||
self.delay = Motor(self.Id + "-M424:MOT")
|
||||
self.delayTime = DelayStage(self.delay)
|
||||
|
||||
|
||||
def get_adjustable_positions_str(self):
|
||||
ostr = '*****PSEN motor positions******\n'
|
||||
ostr = "*****PSEN motor positions******\n"
|
||||
|
||||
for tkey, item in self.__dict__.items():
|
||||
if hasattr(item, 'get_current_value'):
|
||||
if hasattr(item, "get_current_value"):
|
||||
pos = item.get_current_value()
|
||||
ostr += ' ' + tkey.ljust(10) + ' : % 14g\n'%pos
|
||||
ostr += " " + tkey.ljust(10) + " : % 14g\n" % pos
|
||||
return ostr
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
return self.get_adjustable_positions_str()
|
||||
|
||||
|
||||
@@ -2,16 +2,17 @@ from epics import PV
|
||||
|
||||
|
||||
class AttenuatorAramis:
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self._pv_status_str = PV(Id + ':MOT2TRANS.VALD')
|
||||
self._pv_status_int = PV(Id + ':IDX_RB')
|
||||
self._pv_status_str = PV(Id + ":MOT2TRANS.VALD")
|
||||
self._pv_status_int = PV(Id + ":IDX_RB")
|
||||
|
||||
def updateE(self, energy = None):
|
||||
def updateE(self, energy=None):
|
||||
if energy == None:
|
||||
energy = PV("SARUN03-UIND030:FELPHOTENE").value
|
||||
energy = energy * 1000
|
||||
PV(self.Id + ":ENERGY").put(energy)
|
||||
PV(self.Id + ":ENERGY").put(energy)
|
||||
print("Set energy to %s eV" % energy)
|
||||
|
||||
def set_transmission(self, value, energy=None):
|
||||
@@ -40,13 +41,13 @@ class AttenuatorAramis:
|
||||
|
||||
def __repr__(self):
|
||||
t = self.get_transmission()
|
||||
s = '1st harm. transmission = %g\n' % t[0]
|
||||
s += '3rd harm. transmission = %g\n' % t[1]
|
||||
s += 'Targets in beam:\n'
|
||||
s += '%s' % self.get_status()[0]
|
||||
s = "1st harm. transmission = %g\n" % t[0]
|
||||
s += "3rd harm. transmission = %g\n" % t[1]
|
||||
s += "Targets in beam:\n"
|
||||
s += "%s" % self.get_status()[0]
|
||||
return s
|
||||
|
||||
def __call__(self,*args,**kwargs):
|
||||
def __call__(self, *args, **kwargs):
|
||||
self.set_transmission(*args, **kwargs)
|
||||
|
||||
|
||||
|
||||
@@ -6,7 +6,8 @@ from slic.utils.eco_components.aliases import Alias
|
||||
|
||||
|
||||
class AttenuatorAramis:
|
||||
def __init__(self, Id, E_min=1500, sleeptime=1, name=None, set_limits=[-52, 2],pulse_picker=None):
|
||||
|
||||
def __init__(self, Id, E_min=1500, sleeptime=1, name=None, set_limits=[-52, 2], pulse_picker=None):
|
||||
self.Id = Id
|
||||
self.E_min = E_min
|
||||
self._pv_status_str = PV(self.Id + ":MOT2TRANS.VALD")
|
||||
@@ -15,26 +16,20 @@ class AttenuatorAramis:
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
self.pulse_picker = pulse_picker
|
||||
self.motors = [
|
||||
Motor(f"{self.Id}:MOTOR_{n+1}", name=f"motor{n+1}")
|
||||
for n in range(6)
|
||||
]
|
||||
self.motors = [Motor(f"{self.Id}:MOTOR_{n+1}", name=f"motor{n+1}") for n in range(6)]
|
||||
for n, mot in enumerate(self.motors):
|
||||
self.__dict__[f"motor_{n+1}"] = mot
|
||||
self.alias.append(mot.alias)
|
||||
if set_limits:
|
||||
mot.set_limits(*set_limits)
|
||||
|
||||
|
||||
def updateE(self, energy=None):
|
||||
while not energy:
|
||||
energy = PV("SARUN03-UIND030:FELPHOTENE").value
|
||||
energy = energy * 1000
|
||||
if energy < self.E_min:
|
||||
energy = None
|
||||
print(
|
||||
f"Machine photon energy is below {self.E_min} - waiting for the machine to recover"
|
||||
)
|
||||
print(f"Machine photon energy is below {self.E_min} - waiting for the machine to recover")
|
||||
sleep(self._sleeptime)
|
||||
PV(self.Id + ":ENERGY").put(energy)
|
||||
print("Set energy to %s eV" % energy)
|
||||
@@ -53,24 +48,24 @@ class AttenuatorAramis:
|
||||
def setE(self):
|
||||
pass
|
||||
|
||||
def get_transmission(self,verbose=True):
|
||||
def get_transmission(self, verbose=True):
|
||||
tFun = PV(self.Id + ":TRANS_RB").value
|
||||
tTHG = PV(self.Id + ":TRANS3EDHARM_RB").value
|
||||
if verbose:
|
||||
print("Transmission Fundamental: %s THG: %s" % (tFun, tTHG))
|
||||
return tFun, tTHG
|
||||
|
||||
def get_current_value(self,*args,**kwargs):
|
||||
return self.get_transmission(*args,verbose=False,**kwargs)[0]
|
||||
def get_current_value(self, *args, **kwargs):
|
||||
return self.get_transmission(*args, verbose=False, **kwargs)[0]
|
||||
|
||||
def set_target_value(self,value,sleeptime=10,hold=False):
|
||||
def set_target_value(self, value, sleeptime=10, hold=False):
|
||||
def changer():
|
||||
self.set_transmission(value)
|
||||
sleep(sleeptime)
|
||||
if self.pulse_picker:
|
||||
self.pulse_picker.open()
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
def get_status(self):
|
||||
s_str = self._pv_status_str.get(as_string=True)
|
||||
|
||||
+102
-107
@@ -9,26 +9,26 @@ from slic.core.task import Task
|
||||
|
||||
class Double_Crystal_Mono_AramisMacro:
|
||||
|
||||
def __init__(self,Id):
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.theta = Motor(Id + ':RX12')
|
||||
self.x = Motor(Id + ':TX12')
|
||||
self.gap = Motor(Id + ':T2')
|
||||
self.roll1 = Motor(Id + ':RZ1')
|
||||
self.roll2 = Motor(Id + ':RZ2')
|
||||
self.pitch2 = Motor(Id + ':RX2')
|
||||
self.theta = Motor(Id + ":RX12")
|
||||
self.x = Motor(Id + ":TX12")
|
||||
self.gap = Motor(Id + ":T2")
|
||||
self.roll1 = Motor(Id + ":RZ1")
|
||||
self.roll2 = Motor(Id + ":RZ2")
|
||||
self.pitch2 = Motor(Id + ":RX2")
|
||||
|
||||
self.energy_rbk = PV(Id + ':ENERGY')
|
||||
self.energy_sp = PV(Id + ':ENERGY_SP')
|
||||
self.moving = PV(Id + ':MOVING')
|
||||
self._stop = PV(Id +':STOP.PROC')
|
||||
self.energy_rbk = PV(Id + ":ENERGY")
|
||||
self.energy_sp = PV(Id + ":ENERGY_SP")
|
||||
self.moving = PV(Id + ":MOVING")
|
||||
self._stop = PV(Id + ":STOP.PROC")
|
||||
|
||||
def move_and_wait(self,value,checktime=.01,precision=.5):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=0.5):
|
||||
self.energy_sp.put(value)
|
||||
while abs(self.wait_for_valid_value()-value)>precision:
|
||||
while abs(self.wait_for_valid_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(hold=hold, stopper=self.stop)
|
||||
|
||||
@@ -43,9 +43,9 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
tval = np.nan
|
||||
while not np.isfinite(tval):
|
||||
tval = self.energy_rbk.get()
|
||||
return(tval)
|
||||
return tval
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self.energy_sp.put(value)
|
||||
|
||||
def is_moving(self):
|
||||
@@ -53,18 +53,18 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
return not bool(inmotion)
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
if not self.is_moving():
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
else:
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
self._currentChange = self.set_target_value(value+startvalue,*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
self._currentChange = self.set_target_value(value + startvalue, *args, **kwargs)
|
||||
|
||||
def wait(self):
|
||||
self._currentChange.wait()
|
||||
@@ -73,23 +73,22 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
s = "**Double crystal monochromator**\n\n"
|
||||
motors = "theta gap x roll1 roll2 pitch2".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self,motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
pvs = "energy_rbk".split()
|
||||
for pv in pvs:
|
||||
s+= " - %s = %.4f\n" %(pv, getattr(self,pv).value)
|
||||
s += " - %s = %.4f\n" % (pv, getattr(self, pv).value)
|
||||
return s
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
|
||||
class EcolEnergy:
|
||||
|
||||
def __init__(self,Id, val='SARCL02-MBND100:P-SET',rb='SARCL02-MBND100:P-READ' ,dmov='SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK'):
|
||||
def __init__(self, Id, val="SARCL02-MBND100:P-SET", rb="SARCL02-MBND100:P-READ", dmov="SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK"):
|
||||
self.Id = Id
|
||||
self.setter = PV(val)
|
||||
self.readback = PV(rb)
|
||||
@@ -99,50 +98,50 @@ class EcolEnergy:
|
||||
def get_current_value(self):
|
||||
return self.readback.get()
|
||||
|
||||
def move_and_wait(self,value,checktime=.01,precision=2):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=2):
|
||||
curr = self.setter.get()
|
||||
while abs(curr-value)>0.1:
|
||||
while abs(curr - value) > 0.1:
|
||||
curr = self.setter.get()
|
||||
self.setter.put(curr + np.sign(value-curr)*.1)
|
||||
self.setter.put(curr + np.sign(value - curr) * 0.1)
|
||||
sleep(0.3)
|
||||
|
||||
self.setter.put(value)
|
||||
while abs(self.get_current_value() - value)>precision:
|
||||
while abs(self.get_current_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
while not self.dmov.get():
|
||||
#print(self.dmov.get())
|
||||
# print(self.dmov.get())
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
|
||||
class Double_Crystal_Mono(BaseDevice):
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.z_undulator = z_undulator
|
||||
self.description = description
|
||||
|
||||
self.theta = Motor(Id + ':RX12')
|
||||
self.x = Motor(Id + ':TX12')
|
||||
self.gap = Motor(Id + ':T2')
|
||||
self.roll1 = Motor(Id + ':RZ1')
|
||||
self.roll2 = Motor(Id + ':RZ2')
|
||||
self.pitch2 = Motor(Id + ':RX2')
|
||||
self.theta = Motor(Id + ":RX12")
|
||||
self.x = Motor(Id + ":TX12")
|
||||
self.gap = Motor(Id + ":T2")
|
||||
self.roll1 = Motor(Id + ":RZ1")
|
||||
self.roll2 = Motor(Id + ":RZ2")
|
||||
self.pitch2 = Motor(Id + ":RX2")
|
||||
|
||||
self.energy_rbk = PV(Id + ':ENERGY')
|
||||
self.energy_sp = PV(Id + ':ENERGY_SP')
|
||||
self.moving = PV(Id + ':MOVING')
|
||||
self._stop = PV(Id +':STOP.PROC')
|
||||
self.energy_rbk = PV(Id + ":ENERGY")
|
||||
self.energy_sp = PV(Id + ":ENERGY_SP")
|
||||
self.moving = PV(Id + ":MOVING")
|
||||
self._stop = PV(Id + ":STOP.PROC")
|
||||
|
||||
def move_and_wait(self,value,checktime=.01,precision=.5):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=0.5):
|
||||
self.energy_sp.put(value)
|
||||
while abs(self.wait_for_valid_value()-value)>precision:
|
||||
while abs(self.wait_for_valid_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold, stopper=self.stop)
|
||||
|
||||
@@ -157,9 +156,9 @@ class Double_Crystal_Mono(BaseDevice):
|
||||
tval = np.nan
|
||||
while not np.isfinite(tval):
|
||||
tval = self.energy_rbk.get()
|
||||
return(tval)
|
||||
return tval
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self.energy_sp.put(value)
|
||||
|
||||
def is_moving(self):
|
||||
@@ -167,18 +166,18 @@ class Double_Crystal_Mono(BaseDevice):
|
||||
return not bool(inmotion)
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
if not self.is_moving():
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
else:
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
self._currentChange = self.set_target_value(value+startvalue,*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
self._currentChange = self.set_target_value(value + startvalue, *args, **kwargs)
|
||||
|
||||
def wait(self):
|
||||
self._currentChange.wait()
|
||||
@@ -187,23 +186,22 @@ class Double_Crystal_Mono(BaseDevice):
|
||||
s = "**Double crystal monochromator**\n\n"
|
||||
motors = "theta gap x roll1 roll2 pitch2".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self,motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
pvs = "energy_rbk".split()
|
||||
for pv in pvs:
|
||||
s+= " - %s = %.4f\n" %(pv, getattr(self,pv).value)
|
||||
s += " - %s = %.4f\n" % (pv, getattr(self, pv).value)
|
||||
return s
|
||||
|
||||
def __repr__(self):
|
||||
return self.__str__()
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
|
||||
class EcolEnergy:
|
||||
|
||||
def __init__(self,Id, val='SARCL02-MBND100:P-SET',rb='SARCL02-MBND100:P-READ' ,dmov='SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK'):
|
||||
def __init__(self, Id, val="SARCL02-MBND100:P-SET", rb="SARCL02-MBND100:P-READ", dmov="SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK"):
|
||||
self.Id = Id
|
||||
self.setter = PV(val)
|
||||
self.readback = PV(rb)
|
||||
@@ -213,79 +211,76 @@ class EcolEnergy:
|
||||
def get_current_value(self):
|
||||
return self.readback.get()
|
||||
|
||||
def move_and_wait(self,value,checktime=.01,precision=2):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=2):
|
||||
curr = self.setter.get()
|
||||
while abs(curr-value)>0.1:
|
||||
while abs(curr - value) > 0.1:
|
||||
curr = self.setter.get()
|
||||
self.setter.put(curr + np.sign(value-curr)*.1)
|
||||
self.setter.put(curr + np.sign(value - curr) * 0.1)
|
||||
sleep(0.3)
|
||||
|
||||
self.setter.put(value)
|
||||
while abs(self.get_current_value() - value)>precision:
|
||||
while abs(self.get_current_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
while not self.dmov.get():
|
||||
#print(self.dmov.get())
|
||||
# print(self.dmov.get())
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
|
||||
class MonoEcolEnergy:
|
||||
|
||||
def __init__(self,Id):
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.name = 'energy_collimator'
|
||||
self.name = "energy_collimator"
|
||||
self.dcm = Double_Crystal_Mono(Id)
|
||||
self.ecol = EcolEnergy('ecol_dummy')
|
||||
self.ecol = EcolEnergy("ecol_dummy")
|
||||
self.offset = None
|
||||
self.MeVperEV = 0.78333
|
||||
|
||||
def get_current_value(self):
|
||||
return self.dcm.get_current_value()
|
||||
|
||||
def move_and_wait(self,value):
|
||||
ch = [self.dcm.set_target_value(value),
|
||||
self.ecol.set_target_value(self.calcEcol(value))]
|
||||
def move_and_wait(self, value):
|
||||
ch = [self.dcm.set_target_value(value), self.ecol.set_target_value(self.calcEcol(value))]
|
||||
for tc in ch:
|
||||
tc.wait()
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold, stopper=self.dcm.stop)
|
||||
|
||||
def alignOffsets(self):
|
||||
mrb = self.dcm.get_current_value()
|
||||
erb = self.ecol.get_current_value()
|
||||
self.offset = {'dcm':mrb, 'ecol':erb}
|
||||
|
||||
def calcEcol(self,eV):
|
||||
return (eV-self.offset['dcm'])*self.MeVperEV + self.offset['ecol']
|
||||
self.offset = {"dcm": mrb, "ecol": erb}
|
||||
|
||||
def calcEcol(self, eV):
|
||||
return (eV - self.offset["dcm"]) * self.MeVperEV + self.offset["ecol"]
|
||||
|
||||
|
||||
class AlvraDCM_FEL:
|
||||
|
||||
def __init__(self,Id):
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.name = 'Alvra DCM monochromator coupled to FEL beam'
|
||||
self.name = "Alvra DCM monochromator coupled to FEL beam"
|
||||
# self.IOCstatus = PV('ALVRA:running') # bool 0 running, 1 not running
|
||||
self._FELcoupling = PV('SGE-OP2E-ARAMIS:MODE_SP') # string "Off" or "e-beam"
|
||||
self._setEnergy = PV('SAROP11-ARAMIS:ENERGY_SP_USER') # float eV
|
||||
self._getEnergy = PV('SAROP11-ARAMIS:ENERGY') # float eV
|
||||
self.ebeamEnergy = PV('SARCL02-MBND100:P-READ') # float MeV/c
|
||||
self.ebeamEnergySP = PV('SGE-OP2E-ARAMIS:E_ENERGY_SP') # float MeV
|
||||
self.dcmStop = PV('SAROP11-ODCM105:STOP.PROC') # stop the DCM motors
|
||||
self.dcmMoving = PV('SAROP11-ODCM105:MOVING') # DCM moving field
|
||||
self._energyChanging = PV('SGE-OP2E-ARAMIS:MOVING') # PV telling you something related to the energy is changing
|
||||
self._alvraMode = PV('SAROP11-ARAMIS:MODE') # string Aramis SAROP11 mode
|
||||
self.ebeamOK = PV('SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK') # is ebeam no longer changing
|
||||
self.photCalib1 = PV('SGE-OP2E-ARAMIS:PH2E_X1') # photon energy calibration low calibration point
|
||||
self.photCalib2 = PV('SGE-OP2E-ARAMIS:PH2E_X2') # photon energy calibration high calibration point
|
||||
self.ebeamCalib1 = PV('SGE-OP2E-ARAMIS:PH2E_Y1') # electron energy calibration low calibration point
|
||||
self.ebeamCalib2 = PV('SGE-OP2E-ARAMIS:PH2E_Y2') # electron energy calibration high calibration point
|
||||
self._FELcoupling = PV("SGE-OP2E-ARAMIS:MODE_SP") # string "Off" or "e-beam"
|
||||
self._setEnergy = PV("SAROP11-ARAMIS:ENERGY_SP_USER") # float eV
|
||||
self._getEnergy = PV("SAROP11-ARAMIS:ENERGY") # float eV
|
||||
self.ebeamEnergy = PV("SARCL02-MBND100:P-READ") # float MeV/c
|
||||
self.ebeamEnergySP = PV("SGE-OP2E-ARAMIS:E_ENERGY_SP") # float MeV
|
||||
self.dcmStop = PV("SAROP11-ODCM105:STOP.PROC") # stop the DCM motors
|
||||
self.dcmMoving = PV("SAROP11-ODCM105:MOVING") # DCM moving field
|
||||
self._energyChanging = PV("SGE-OP2E-ARAMIS:MOVING") # PV telling you something related to the energy is changing
|
||||
self._alvraMode = PV("SAROP11-ARAMIS:MODE") # string Aramis SAROP11 mode
|
||||
self.ebeamOK = PV("SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK") # is ebeam no longer changing
|
||||
self.photCalib1 = PV("SGE-OP2E-ARAMIS:PH2E_X1") # photon energy calibration low calibration point
|
||||
self.photCalib2 = PV("SGE-OP2E-ARAMIS:PH2E_X2") # photon energy calibration high calibration point
|
||||
self.ebeamCalib1 = PV("SGE-OP2E-ARAMIS:PH2E_Y1") # electron energy calibration low calibration point
|
||||
self.ebeamCalib2 = PV("SGE-OP2E-ARAMIS:PH2E_Y2") # electron energy calibration high calibration point
|
||||
|
||||
def __str__(self):
|
||||
# ioc = self.IOCstatus.get()
|
||||
@@ -302,26 +297,26 @@ class AlvraDCM_FEL:
|
||||
ebeamCalib1Str = self.ebeamCalib1.get()
|
||||
ebeamCalib2Str = self.ebeamCalib2.get()
|
||||
|
||||
s = '**Alvra DCM-FEL status**\n\n'
|
||||
s = "**Alvra DCM-FEL status**\n\n"
|
||||
# print('%s'%iocStr)
|
||||
# print('FEL coupling %s'%FELcouplingStr)
|
||||
# print('Alvra beamline mode %s'%alvraModeStr)
|
||||
# print('Photon energy (eV) %'%currEnergy)
|
||||
# s += '%s\n'%iocStr
|
||||
s += 'FEL coupling: %s\n'%FELcouplingStr
|
||||
s += 'Alvra beamline mode: %s\n'%alvraModeStr
|
||||
s += 'Photon energy: %.2f eV\n'%currEnergy
|
||||
s += 'Electron energy: %.2f MeV\n'%currebeamEnergy
|
||||
s += 'Calibration set points:\n'
|
||||
s += ' Low: Photon %.2f keV, Electron %.2f MeV\n'%(photCalib1Str, ebeamCalib1Str)
|
||||
s += ' High: Photon %.2f keV, Electron %.2f MeV\n'%(photCalib2Str, ebeamCalib2Str)
|
||||
s += "FEL coupling: %s\n" % FELcouplingStr
|
||||
s += "Alvra beamline mode: %s\n" % alvraModeStr
|
||||
s += "Photon energy: %.2f eV\n" % currEnergy
|
||||
s += "Electron energy: %.2f MeV\n" % currebeamEnergy
|
||||
s += "Calibration set points:\n"
|
||||
s += " Low: Photon %.2f keV, Electron %.2f MeV\n" % (photCalib1Str, ebeamCalib1Str)
|
||||
s += " High: Photon %.2f keV, Electron %.2f MeV\n" % (photCalib2Str, ebeamCalib2Str)
|
||||
return s
|
||||
|
||||
def get_current_value(self):
|
||||
return self._getEnergy.get()
|
||||
|
||||
def move_and_wait(self,value,checktime=.1,precision=0.5):
|
||||
self._FELcoupling.put(1) # ensure the FEL coupling is turned on
|
||||
def move_and_wait(self, value, checktime=0.1, precision=0.5):
|
||||
self._FELcoupling.put(1) # ensure the FEL coupling is turned on
|
||||
self._setEnergy.put(value)
|
||||
# while self.ebeamOK.get()==0:
|
||||
# sleep(checktime)
|
||||
@@ -332,7 +327,7 @@ class AlvraDCM_FEL:
|
||||
while self._energyChanging == 1:
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
@@ -3,36 +3,36 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class KBhor:
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
self.x = Motor(Id + ':W_X')
|
||||
self.y = Motor(Id + ':W_Y')
|
||||
self.pitch = Motor(Id + ':W_RY')
|
||||
self.roll = Motor(Id + ':W_RZ')
|
||||
self.yaw = Motor(Id + ':W_RX')
|
||||
self.bend1 = Motor(Id + ':BU')
|
||||
self.bend2 = Motor(Id + ':BD')
|
||||
self.x = Motor(Id + ":W_X")
|
||||
self.y = Motor(Id + ":W_Y")
|
||||
self.pitch = Motor(Id + ":W_RY")
|
||||
self.roll = Motor(Id + ":W_RZ")
|
||||
self.yaw = Motor(Id + ":W_RX")
|
||||
self.bend1 = Motor(Id + ":BU")
|
||||
self.bend2 = Motor(Id + ":BD")
|
||||
|
||||
self.mode = PV(Id[:11]+':MODE').enum_strs[PV(Id[:11]+':MODE').value]
|
||||
self.mode = PV(Id[:11] + ":MODE").enum_strs[PV(Id[:11] + ":MODE").value]
|
||||
|
||||
#### actual motors ###
|
||||
self._Y1 = Motor(Id + ':TY1')
|
||||
self._Y2 = Motor(Id + ':TY2')
|
||||
self._Y3 = Motor(Id + ':TY3')
|
||||
self._X1 = Motor(Id + ':TX1')
|
||||
self._X2 = Motor(Id + ':TX2')
|
||||
|
||||
self._Y1 = Motor(Id + ":TY1")
|
||||
self._Y2 = Motor(Id + ":TY2")
|
||||
self._Y3 = Motor(Id + ":TY3")
|
||||
self._X1 = Motor(Id + ":TX1")
|
||||
self._X2 = Motor(Id + ":TX2")
|
||||
|
||||
def __repr__(self):
|
||||
s = "**Horizontal KB mirror**\n"
|
||||
motors = "bend1 bend2 pitch roll yaw x y".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self,motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n**Stages**\n"
|
||||
stages = "_Y1 _Y2 _Y3 _X1 _X2".split()
|
||||
for stage in stages:
|
||||
s+= " - %s = %.4f\n" %(stage, getattr(self,stage).wm())
|
||||
s += " - %s = %.4f\n" % (stage, getattr(self, stage).wm())
|
||||
return s
|
||||
|
||||
|
||||
|
||||
@@ -3,35 +3,36 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class KBver:
|
||||
|
||||
def __init__(self, Id, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
|
||||
self.x = Motor(Id + ':W_X')
|
||||
self.y = Motor(Id + ':W_Y')
|
||||
self.pitch = Motor(Id + ':W_RX')
|
||||
self.roll = Motor(Id + ':W_RZ')
|
||||
self.yaw = Motor(Id + ':W_RY')
|
||||
self.bend1 = Motor(Id + ':BU')
|
||||
self.bend2 = Motor(Id + ':BD')
|
||||
self.x = Motor(Id + ":W_X")
|
||||
self.y = Motor(Id + ":W_Y")
|
||||
self.pitch = Motor(Id + ":W_RX")
|
||||
self.roll = Motor(Id + ":W_RZ")
|
||||
self.yaw = Motor(Id + ":W_RY")
|
||||
self.bend1 = Motor(Id + ":BU")
|
||||
self.bend2 = Motor(Id + ":BD")
|
||||
|
||||
self.mode = PV(Id[:11]+':MODE').enum_strs[PV(Id[:11]+':MODE').value]
|
||||
self.mode = PV(Id[:11] + ":MODE").enum_strs[PV(Id[:11] + ":MODE").value]
|
||||
|
||||
#### actual motors ###
|
||||
self._Y1 = Motor(Id + ':TY1')
|
||||
self._Y2 = Motor(Id + ':TY2')
|
||||
self._Y3 = Motor(Id + ':TY3')
|
||||
self._X1 = Motor(Id + ':TX1')
|
||||
self._X2 = Motor(Id + ':TX2')
|
||||
self._Y1 = Motor(Id + ":TY1")
|
||||
self._Y2 = Motor(Id + ":TY2")
|
||||
self._Y3 = Motor(Id + ":TY3")
|
||||
self._X1 = Motor(Id + ":TX1")
|
||||
self._X2 = Motor(Id + ":TX2")
|
||||
|
||||
def __repr__(self):
|
||||
s = "**Vertical KB mirror**\n"
|
||||
motors = "bend1 bend2 pitch roll yaw x y".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self,motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
s += "\n**Stages**\n"
|
||||
stages = "_Y1 _Y2 _Y3 _X1 _X2".split()
|
||||
for stage in stages:
|
||||
s+= " - %s = %.4f\n" %(stage, getattr(self,stage).wm())
|
||||
s += " - %s = %.4f\n" % (stage, getattr(self, stage).wm())
|
||||
return s
|
||||
|
||||
|
||||
|
||||
@@ -13,6 +13,7 @@ def addMotorToSelf(self, name=None, Id=None):
|
||||
|
||||
|
||||
class OffsetMirror:
|
||||
|
||||
def __init__(self, name=None, Id=None, alias_namespace=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
|
||||
@@ -15,6 +15,7 @@ def addMotorToSelf(self, name=None, Id=None):
|
||||
|
||||
|
||||
class Pulsepick:
|
||||
|
||||
def __init__(self, Id=None, evronoff=None, evrsrc=None, name=None):
|
||||
self.name = name
|
||||
self.alias = Alias(name)
|
||||
@@ -52,15 +53,15 @@ class Pulsepick:
|
||||
|
||||
def get_status(self):
|
||||
stat = self._evrsrc.get()
|
||||
if stat==62 and self._openclose.get()==1:
|
||||
return 'open'
|
||||
if self._openclose.get()==0:
|
||||
return 'closed'
|
||||
if stat == 62 and self._openclose.get() == 1:
|
||||
return "open"
|
||||
if self._openclose.get() == 0:
|
||||
return "closed"
|
||||
else:
|
||||
return 'unknown'
|
||||
return "unknown"
|
||||
|
||||
def __repr__(self):
|
||||
return f'FEL pulse picker state {self.get_status()}.'
|
||||
return f"FEL pulse picker state {self.get_status()}."
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3,14 +3,14 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class RefLaser_Aramis:
|
||||
|
||||
def __init__(self, Id, elog=None, name=None, inpos=-18.818, outpos=-5, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.elog = elog
|
||||
self.name = name
|
||||
self._inpos = inpos
|
||||
self._outpos = outpos
|
||||
self.mirrmotor = Motor(self.Id + ':MOTOR_1')
|
||||
|
||||
self.mirrmotor = Motor(self.Id + ":MOTOR_1")
|
||||
|
||||
def __call__(self, *args, **kwargs):
|
||||
self.set(*args, **kwargs)
|
||||
@@ -19,16 +19,16 @@ class RefLaser_Aramis:
|
||||
status = self.get_status()
|
||||
if status:
|
||||
return "Reflaser is In."
|
||||
elif status==False:
|
||||
elif status == False:
|
||||
return "Reflaser is Out."
|
||||
elif status==None:
|
||||
return "Reflaser status not defined."
|
||||
elif status == None:
|
||||
return "Reflaser status not defined."
|
||||
|
||||
def get_status(self):
|
||||
v = self.mirrmotor.get_current_value()
|
||||
if abs(v - self._inpos) < .2:
|
||||
if abs(v - self._inpos) < 0.2:
|
||||
isin = True
|
||||
elif abs(v - self._outpos) < .2:
|
||||
elif abs(v - self._outpos) < 0.2:
|
||||
isin = False
|
||||
else:
|
||||
isin = None
|
||||
@@ -36,12 +36,12 @@ class RefLaser_Aramis:
|
||||
|
||||
def set(self, value):
|
||||
if type(value) is str:
|
||||
if value.lower()=='in':
|
||||
if value.lower() == "in":
|
||||
value = True
|
||||
elif value.lower()=='out':
|
||||
elif value.lower() == "out":
|
||||
value = False
|
||||
else:
|
||||
print('String %s not recognized!'%value)
|
||||
print("String %s not recognized!" % value)
|
||||
if value:
|
||||
self.mirrmotor.set_target_value(self._inpos)
|
||||
else:
|
||||
|
||||
@@ -2,136 +2,138 @@ from slic.devices.general.motor import Motor
|
||||
|
||||
|
||||
class SlitBlades_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
self._x1 = Motor(Id + ':MOTOR_X1')
|
||||
self._x2 = Motor(Id + ':MOTOR_X2')
|
||||
self._y1 = Motor(Id + ':MOTOR_Y1')
|
||||
self._y2 = Motor(Id + ':MOTOR_Y2')
|
||||
self._x1 = Motor(Id + ":MOTOR_X1")
|
||||
self._x2 = Motor(Id + ":MOTOR_X2")
|
||||
self._y1 = Motor(Id + ":MOTOR_Y1")
|
||||
self._y2 = Motor(Id + ":MOTOR_Y2")
|
||||
|
||||
def get_hg(self):
|
||||
return self._x2.get_current_value()-self._x1.get_current_value()
|
||||
return self._x2.get_current_value() - self._x1.get_current_value()
|
||||
|
||||
def get_vg(self):
|
||||
return self._y2.get_current_value()-self._y1.get_current_value()
|
||||
return self._y2.get_current_value() - self._y1.get_current_value()
|
||||
|
||||
def get_ho(self):
|
||||
return (self._x1.get_current_value()+self._x2.get_current_value())/2
|
||||
return (self._x1.get_current_value() + self._x2.get_current_value()) / 2
|
||||
|
||||
def get_vo(self):
|
||||
return (self._y1.get_current_value()+self._y2.get_current_value())/2
|
||||
return (self._y1.get_current_value() + self._y2.get_current_value()) / 2
|
||||
|
||||
def set_hg(self,value):
|
||||
def set_hg(self, value):
|
||||
ho = self.get_ho()
|
||||
c1 = self._x1.set_target_value(ho-value/2)
|
||||
c2 = self._x2.set_target_value(ho+value/2)
|
||||
return c1,c2
|
||||
c1 = self._x1.set_target_value(ho - value / 2)
|
||||
c2 = self._x2.set_target_value(ho + value / 2)
|
||||
return c1, c2
|
||||
|
||||
def set_vg(self,value):
|
||||
def set_vg(self, value):
|
||||
vo = self.get_vo()
|
||||
c1 = self._y1.set_target_value(vo-value/2)
|
||||
c2 = self._y2.set_target_value(vo+value/2)
|
||||
return c1,c2
|
||||
c1 = self._y1.set_target_value(vo - value / 2)
|
||||
c2 = self._y2.set_target_value(vo + value / 2)
|
||||
return c1, c2
|
||||
|
||||
def set_ho(self,value):
|
||||
def set_ho(self, value):
|
||||
hg = self.get_hg()
|
||||
c1 = self._x1.set_target_value(value-hg/2)
|
||||
c2 = self._x2.set_target_value(value+hg/2)
|
||||
return c1,c2
|
||||
c1 = self._x1.set_target_value(value - hg / 2)
|
||||
c2 = self._x2.set_target_value(value + hg / 2)
|
||||
return c1, c2
|
||||
|
||||
def set_vo(self,value):
|
||||
def set_vo(self, value):
|
||||
vg = self.get_vg()
|
||||
c1 = self._y1.set_target_value(value-vg/2)
|
||||
c2 = self._y2.set_target_value(value+vg/2)
|
||||
return c1,c2
|
||||
c1 = self._y1.set_target_value(value - vg / 2)
|
||||
c2 = self._y2.set_target_value(value + vg / 2)
|
||||
return c1, c2
|
||||
|
||||
def __call__(self,width,height):
|
||||
def __call__(self, width, height):
|
||||
self.set_hg(width)
|
||||
self.set_vg(height)
|
||||
|
||||
def __repr__(self):
|
||||
string1 = 'gap: (%g,%g) mm'%(self.get_hg(),self.get_vg())
|
||||
string2 = 'pos: (%g,%g) mm'%(self.get_ho(),self.get_vo())
|
||||
return '\n'.join((string1,string2))
|
||||
string1 = "gap: (%g,%g) mm" % (self.get_hg(), self.get_vg())
|
||||
string2 = "pos: (%g,%g) mm" % (self.get_ho(), self.get_vo())
|
||||
return "\n".join((string1, string2))
|
||||
|
||||
|
||||
class SlitFourBlades_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
self._ax1 = Motor(Id + ':MOTOR_AX1')
|
||||
self._ax2 = Motor(Id + ':MOTOR_AX2')
|
||||
self._ay1 = Motor(Id + ':MOTOR_AY1')
|
||||
self._ay2 = Motor(Id + ':MOTOR_AY2')
|
||||
self._bx1 = Motor(Id + ':MOTOR_BX1')
|
||||
self._bx2 = Motor(Id + ':MOTOR_BX2')
|
||||
self._by1 = Motor(Id + ':MOTOR_BY1')
|
||||
self._by2 = Motor(Id + ':MOTOR_BY2')
|
||||
self._ax1 = Motor(Id + ":MOTOR_AX1")
|
||||
self._ax2 = Motor(Id + ":MOTOR_AX2")
|
||||
self._ay1 = Motor(Id + ":MOTOR_AY1")
|
||||
self._ay2 = Motor(Id + ":MOTOR_AY2")
|
||||
self._bx1 = Motor(Id + ":MOTOR_BX1")
|
||||
self._bx2 = Motor(Id + ":MOTOR_BX2")
|
||||
self._by1 = Motor(Id + ":MOTOR_BY1")
|
||||
self._by2 = Motor(Id + ":MOTOR_BY2")
|
||||
|
||||
def get_hg(self):
|
||||
return self._ax2.get_current_value()-self._ax1.get_current_value()
|
||||
return self._ax2.get_current_value() - self._ax1.get_current_value()
|
||||
|
||||
def get_vg(self):
|
||||
return self._ay2.get_current_value()-self._ay1.get_current_value()
|
||||
return self._ay2.get_current_value() - self._ay1.get_current_value()
|
||||
|
||||
def get_ho(self):
|
||||
return (self._ax1.get_current_value()+self._ax2.get_current_value())/2
|
||||
return (self._ax1.get_current_value() + self._ax2.get_current_value()) / 2
|
||||
|
||||
def get_vo(self):
|
||||
return (self._ay1.get_current_value()+self._ay2.get_current_value())/2
|
||||
return (self._ay1.get_current_value() + self._ay2.get_current_value()) / 2
|
||||
|
||||
def set_hg(self,value):
|
||||
def set_hg(self, value):
|
||||
ho = self.get_ho()
|
||||
c1 = self._ax1.set_target_value(ho-value/2)
|
||||
c2 = self._ax2.set_target_value(ho+value/2)
|
||||
c3 = self._bx1.set_target_value(ho-value/2)
|
||||
c4 = self._bx2.set_target_value(ho+value/2)
|
||||
return c1,c2,c3,c4
|
||||
c1 = self._ax1.set_target_value(ho - value / 2)
|
||||
c2 = self._ax2.set_target_value(ho + value / 2)
|
||||
c3 = self._bx1.set_target_value(ho - value / 2)
|
||||
c4 = self._bx2.set_target_value(ho + value / 2)
|
||||
return c1, c2, c3, c4
|
||||
|
||||
def set_vg(self,value):
|
||||
def set_vg(self, value):
|
||||
vo = self.get_vo()
|
||||
c1 = self._ay1.set_target_value(vo-value/2)
|
||||
c2 = self._ay2.set_target_value(vo+value/2)
|
||||
c3 = self._by1.set_target_value(vo-value/2)
|
||||
c4 = self._by2.set_target_value(vo+value/2)
|
||||
return c1,c2,c3,c4
|
||||
c1 = self._ay1.set_target_value(vo - value / 2)
|
||||
c2 = self._ay2.set_target_value(vo + value / 2)
|
||||
c3 = self._by1.set_target_value(vo - value / 2)
|
||||
c4 = self._by2.set_target_value(vo + value / 2)
|
||||
return c1, c2, c3, c4
|
||||
|
||||
def set_ho(self,value):
|
||||
def set_ho(self, value):
|
||||
hg = self.get_hg()
|
||||
c1 = self._ax1.set_target_value(value-hg/2)
|
||||
c2 = self._ax2.set_target_value(value+hg/2)
|
||||
c3 = self._bx1.set_target_value(value-hg/2)
|
||||
c4 = self._bx2.set_target_value(value+hg/2)
|
||||
return c1,c2,c3,c4
|
||||
c1 = self._ax1.set_target_value(value - hg / 2)
|
||||
c2 = self._ax2.set_target_value(value + hg / 2)
|
||||
c3 = self._bx1.set_target_value(value - hg / 2)
|
||||
c4 = self._bx2.set_target_value(value + hg / 2)
|
||||
return c1, c2, c3, c4
|
||||
|
||||
def set_vo(self,value):
|
||||
def set_vo(self, value):
|
||||
vg = self.get_vg()
|
||||
c1 = self._ay1.set_target_value(value-vg/2)
|
||||
c2 = self._ay2.set_target_value(value+vg/2)
|
||||
c3 = self._by1.set_target_value(value-vg/2)
|
||||
c4 = self._by2.set_target_value(value+vg/2)
|
||||
return c1,c2,c3,c4
|
||||
c1 = self._ay1.set_target_value(value - vg / 2)
|
||||
c2 = self._ay2.set_target_value(value + vg / 2)
|
||||
c3 = self._by1.set_target_value(value - vg / 2)
|
||||
c4 = self._by2.set_target_value(value + vg / 2)
|
||||
return c1, c2, c3, c4
|
||||
|
||||
def __call__(self,width,height):
|
||||
def __call__(self, width, height):
|
||||
self.set_hg(width)
|
||||
self.set_vg(height)
|
||||
|
||||
def __repr__(self):
|
||||
string1 = 'gap: (%g,%g) mm'%(self.get_hg(),self.get_vg())
|
||||
string2 = 'pos: (%g,%g) mm'%(self.get_ho(),self.get_vo())
|
||||
return '\n'.join((string1,string2))
|
||||
|
||||
string1 = "gap: (%g,%g) mm" % (self.get_hg(), self.get_vg())
|
||||
string2 = "pos: (%g,%g) mm" % (self.get_ho(), self.get_vo())
|
||||
return "\n".join((string1, string2))
|
||||
|
||||
|
||||
class SlitPosWidth_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None, z_undulator=None, description=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
self._xoffs = Motor(Id + ':MOTOR_X')
|
||||
self._yoffs = Motor(Id + ':MOTOR_Y')
|
||||
self._xgap = Motor(Id + ':MOTOR_W')
|
||||
self._ygap = Motor(Id + ':MOTOR_H')
|
||||
self._xoffs = Motor(Id + ":MOTOR_X")
|
||||
self._yoffs = Motor(Id + ":MOTOR_Y")
|
||||
self._xgap = Motor(Id + ":MOTOR_W")
|
||||
self._ygap = Motor(Id + ":MOTOR_H")
|
||||
|
||||
def get_hg(self):
|
||||
return self._xgap.get_current_value()
|
||||
@@ -145,30 +147,30 @@ class SlitPosWidth_old:
|
||||
def get_vo(self):
|
||||
return self._yoffs.get_current_value()
|
||||
|
||||
def set_hg(self,value):
|
||||
def set_hg(self, value):
|
||||
c = self._xgap.set_target_value(value)
|
||||
return c
|
||||
|
||||
def set_vg(self,value):
|
||||
def set_vg(self, value):
|
||||
c = self._ygap.set_target_value(value)
|
||||
return c
|
||||
|
||||
def set_ho(self,value):
|
||||
def set_ho(self, value):
|
||||
c = self._xoffs.set_target_value(value)
|
||||
return c
|
||||
|
||||
def set_vo(self,value):
|
||||
def set_vo(self, value):
|
||||
c = self._yoffs.set_target_value(value)
|
||||
return c
|
||||
|
||||
def __call__(self,width,height):
|
||||
def __call__(self, width, height):
|
||||
self.set_hg(width)
|
||||
self.set_vg(height)
|
||||
|
||||
def __repr__(self):
|
||||
string1 = 'gap: (%g,%g) mm'%(self.get_hg(),self.get_vg())
|
||||
string2 = 'pos: (%g,%g) mm'%(self.get_ho(),self.get_vo())
|
||||
return '\n'.join((string1,string2))
|
||||
string1 = "gap: (%g,%g) mm" % (self.get_hg(), self.get_vg())
|
||||
string2 = "pos: (%g,%g) mm" % (self.get_ho(), self.get_vo())
|
||||
return "\n".join((string1, string2))
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -8,11 +8,14 @@ def addSlitRepr(Slitobj):
|
||||
def repr(self):
|
||||
s = f"pos ({self.hpos.get_current_value():6.3f},{self.vpos.get_current_value():6.3f}), gap ({self.hgap.get_current_value():6.3f},{self.vgap.get_current_value():6.3f})"
|
||||
return s
|
||||
Slitobj.__repr__ = repr
|
||||
|
||||
Slitobj.__repr__ = repr
|
||||
return Slitobj
|
||||
|
||||
|
||||
@addSlitRepr
|
||||
class SlitBlades:
|
||||
|
||||
def __init__(self, pvname, name=None, elog=None):
|
||||
self.name = name
|
||||
self.Id = pvname
|
||||
@@ -45,40 +48,16 @@ class SlitBlades:
|
||||
return tuple([tx + self.vgap.get_current_value() for tx in [-x / 2, x / 2]])
|
||||
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.right, self.left],
|
||||
getgap,
|
||||
setwidth,
|
||||
reset_current_value_to=True,
|
||||
name="hgap",
|
||||
self, AdjustableVirtual, [self.right, self.left], getgap, setwidth, reset_current_value_to=True, name="hgap",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.down, self.up],
|
||||
getgap,
|
||||
setheight,
|
||||
reset_current_value_to=True,
|
||||
name="vgap",
|
||||
self, AdjustableVirtual, [self.down, self.up], getgap, setheight, reset_current_value_to=True, name="vgap",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.right, self.left],
|
||||
getpos,
|
||||
sethpos,
|
||||
reset_current_value_to=True,
|
||||
name="hpos",
|
||||
self, AdjustableVirtual, [self.right, self.left], getpos, sethpos, reset_current_value_to=True, name="hpos",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.down, self.up],
|
||||
getpos,
|
||||
setvpos,
|
||||
reset_current_value_to=True,
|
||||
name="vpos",
|
||||
self, AdjustableVirtual, [self.down, self.up], getpos, setvpos, reset_current_value_to=True, name="vpos",
|
||||
)
|
||||
|
||||
def __call__(self, *args):
|
||||
@@ -103,8 +82,10 @@ class SlitBlades:
|
||||
else:
|
||||
raise Exception("wrong number of input arguments!")
|
||||
|
||||
|
||||
@addSlitRepr
|
||||
class SlitPosWidth:
|
||||
|
||||
def __init__(self, pvname, name=None, elog=None):
|
||||
self.name = name
|
||||
self.Id = pvname
|
||||
@@ -114,14 +95,14 @@ class SlitPosWidth:
|
||||
append_object_to_object(self, Motor, pvname + ":MOTOR_W", name="hgap")
|
||||
append_object_to_object(self, Motor, pvname + ":MOTOR_H", name="vgap")
|
||||
|
||||
def getblade(pos,gap,direction=1):
|
||||
return pos + direction*gap/2
|
||||
def getblade(pos, gap, direction=1):
|
||||
return pos + direction * gap / 2
|
||||
|
||||
def setblade(bde,pos,gap,direction=1):
|
||||
delta = bde-getblade(pos,gap,direction=direction)
|
||||
ngap = gap + direction*delta
|
||||
npos = pos + direction*delta/2
|
||||
return npos,ngap
|
||||
def setblade(bde, pos, gap, direction=1):
|
||||
delta = bde - getblade(pos, gap, direction=direction)
|
||||
ngap = gap + direction * delta
|
||||
npos = pos + direction * delta / 2
|
||||
return npos, ngap
|
||||
|
||||
def getpos(xn, xp):
|
||||
return (xn + xp) / 2
|
||||
@@ -138,42 +119,10 @@ class SlitPosWidth:
|
||||
def setvpos(x):
|
||||
return tuple([tx + self.vgap.get_current_value() for tw in [-x / 2, x / 2]])
|
||||
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.vpos, self.vgap],
|
||||
partial(getblade,direction=1),
|
||||
partial(setblade,direction=1),
|
||||
reset_current_value_to=True,
|
||||
name="up"
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.vpos, self.vgap],
|
||||
partial(getblade,direction=-1),
|
||||
partial(setblade,direction=-1),
|
||||
reset_current_value_to=True,
|
||||
name="down"
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.hpos, self.hgap],
|
||||
partial(getblade,direction=1),
|
||||
partial(setblade,direction=1),
|
||||
reset_current_value_to=True,
|
||||
name="left"
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.hpos, self.hgap],
|
||||
partial(getblade,direction=-1),
|
||||
partial(setblade,direction=-1),
|
||||
reset_current_value_to=True,
|
||||
name="right"
|
||||
)
|
||||
append_object_to_object(self, AdjustableVirtual, [self.vpos, self.vgap], partial(getblade, direction=1), partial(setblade, direction=1), reset_current_value_to=True, name="up")
|
||||
append_object_to_object(self, AdjustableVirtual, [self.vpos, self.vgap], partial(getblade, direction=-1), partial(setblade, direction=-1), reset_current_value_to=True, name="down")
|
||||
append_object_to_object(self, AdjustableVirtual, [self.hpos, self.hgap], partial(getblade, direction=1), partial(setblade, direction=1), reset_current_value_to=True, name="left")
|
||||
append_object_to_object(self, AdjustableVirtual, [self.hpos, self.hgap], partial(getblade, direction=-1), partial(setblade, direction=-1), reset_current_value_to=True, name="right")
|
||||
|
||||
def __call__(self, *args):
|
||||
if len(args) == 0:
|
||||
@@ -198,9 +147,9 @@ class SlitPosWidth:
|
||||
raise Exception("wrong number of input arguments!")
|
||||
|
||||
|
||||
|
||||
@addSlitRepr
|
||||
class SlitBlades_JJ:
|
||||
|
||||
def __init__(self, pvname, name=None, elog=None):
|
||||
self.name = name
|
||||
self.Id = pvname
|
||||
@@ -229,40 +178,16 @@ class SlitBlades_JJ:
|
||||
return tuple([tx + self.vgap.get_current_value() for tx in [-x / 2, x / 2]])
|
||||
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.right, self.left],
|
||||
getgap,
|
||||
setwidth,
|
||||
reset_current_value_to=True,
|
||||
name="hgap",
|
||||
self, AdjustableVirtual, [self.right, self.left], getgap, setwidth, reset_current_value_to=True, name="hgap",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.down, self.up],
|
||||
getgap,
|
||||
setheight,
|
||||
reset_current_value_to=True,
|
||||
name="vgap",
|
||||
self, AdjustableVirtual, [self.down, self.up], getgap, setheight, reset_current_value_to=True, name="vgap",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.right, self.left],
|
||||
getpos,
|
||||
sethpos,
|
||||
reset_current_value_to=True,
|
||||
name="hpos",
|
||||
self, AdjustableVirtual, [self.right, self.left], getpos, sethpos, reset_current_value_to=True, name="hpos",
|
||||
)
|
||||
append_object_to_object(
|
||||
self,
|
||||
AdjustableVirtual,
|
||||
[self.down, self.up],
|
||||
getpos,
|
||||
setvpos,
|
||||
reset_current_value_to=True,
|
||||
name="vpos",
|
||||
self, AdjustableVirtual, [self.down, self.up], getpos, setvpos, reset_current_value_to=True, name="vpos",
|
||||
)
|
||||
|
||||
def __call__(self, *args):
|
||||
@@ -289,6 +214,7 @@ class SlitBlades_JJ:
|
||||
|
||||
|
||||
class SlitBlades_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -344,6 +270,7 @@ class SlitBlades_old:
|
||||
|
||||
|
||||
class SlitBladesJJ_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -399,6 +326,7 @@ class SlitBladesJJ_old:
|
||||
|
||||
|
||||
class SlitFourBlades_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -469,6 +397,7 @@ class SlitFourBlades_old:
|
||||
|
||||
|
||||
class SlitPosWidth_old:
|
||||
|
||||
def __init__(self, Id, name=None, elog=None):
|
||||
self.Id = Id
|
||||
self.name = name
|
||||
@@ -513,3 +442,6 @@ class SlitPosWidth_old:
|
||||
string1 = "gap: (%g,%g) mm" % (self.get_hg(), self.get_vg())
|
||||
string2 = "pos: (%g,%g) mm" % (self.get_ho(), self.get_vo())
|
||||
return "\n".join((string1, string2))
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -8,25 +8,26 @@ from slic.core.task import Task
|
||||
|
||||
|
||||
class Double_Crystal_Mono_AramisMacro:
|
||||
def __init__(self, Id, timeAdjustable=None, timeReferenceEnergy=None, timeReference=None):
|
||||
self.Id = Id
|
||||
self.theta = Motor(Id + ':RX12')
|
||||
self.x = Motor(Id + ':TX12')
|
||||
self.gap = Motor(Id + ':T2')
|
||||
self.roll1 = Motor(Id + ':RZ1')
|
||||
self.roll2 = Motor(Id + ':RZ2')
|
||||
self.pitch2 = Motor(Id + ':RX2')
|
||||
|
||||
self.energy_rbk = PV(Id + ':ENERGY')
|
||||
self.energy_sp = PV(Id + ':ENERGY_SP')
|
||||
self.moving = PV(Id + ':MOVING')
|
||||
self._stop = PV(Id +':STOP.PROC')
|
||||
self.crystal_type = EnumWrapper(Id + ':CRYSTAL_SP')
|
||||
self.beam_offset = PV(Id + ':BEAM_OFFSET')
|
||||
self.timeAdjustable = timeAdjustable
|
||||
self.timeReferenceEnergy = timeReferenceEnergy
|
||||
self.timeReference = timeReference
|
||||
self.correctTime = False
|
||||
def __init__(self, Id, timeAdjustable=None, timeReferenceEnergy=None, timeReference=None):
|
||||
self.Id = Id
|
||||
self.theta = Motor(Id + ":RX12")
|
||||
self.x = Motor(Id + ":TX12")
|
||||
self.gap = Motor(Id + ":T2")
|
||||
self.roll1 = Motor(Id + ":RZ1")
|
||||
self.roll2 = Motor(Id + ":RZ2")
|
||||
self.pitch2 = Motor(Id + ":RX2")
|
||||
|
||||
self.energy_rbk = PV(Id + ":ENERGY")
|
||||
self.energy_sp = PV(Id + ":ENERGY_SP")
|
||||
self.moving = PV(Id + ":MOVING")
|
||||
self._stop = PV(Id + ":STOP.PROC")
|
||||
self.crystal_type = EnumWrapper(Id + ":CRYSTAL_SP")
|
||||
self.beam_offset = PV(Id + ":BEAM_OFFSET")
|
||||
self.timeAdjustable = timeAdjustable
|
||||
self.timeReferenceEnergy = timeReferenceEnergy
|
||||
self.timeReference = timeReference
|
||||
self.correctTime = False
|
||||
|
||||
def _calcOffsetDetour(self, E, crystal_type=None, beam_offset=None):
|
||||
if not crystal_type:
|
||||
@@ -37,7 +38,7 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
raise NotImplementedError
|
||||
if not beam_offset:
|
||||
beam_offset = self.beam_offset.get()
|
||||
theta = np.arcsin(12398.419739640718/E/2/d)
|
||||
theta = np.arcsin(12398.419739640718 / E / 2 / d)
|
||||
return np.tan(theta) * beam_offset
|
||||
|
||||
def setTimeReference(self, t=None, E=None):
|
||||
@@ -49,14 +50,13 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
self.timeReference = t
|
||||
self.timeReferenceEnergy = E
|
||||
|
||||
def move_and_wait(self, value, checktime=.01, precision=.5):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=0.5):
|
||||
if self.correctTime:
|
||||
p_ref = self._calcOffsetDetour(self.timeReferenceEnergy)
|
||||
p_target = self._calcOffsetDetour(value)
|
||||
t_delta = (p_target-p_ref)*1e-3/299792458.
|
||||
t_delta = (p_target - p_ref) * 1e-3 / 299792458.0
|
||||
t_new = self.timeReference + t_delta
|
||||
print('correcting timing by Dt = {t_delta} s to {t_new} s')
|
||||
|
||||
print("correcting timing by Dt = {t_delta} s to {t_new} s")
|
||||
|
||||
#self.energy_sp.put(value)
|
||||
#while abs(self.wait_for_valid_value()-value)>precision:
|
||||
@@ -77,9 +77,9 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
tval = np.nan
|
||||
while not np.isfinite(tval):
|
||||
tval = self.energy_rbk.get()
|
||||
return(tval)
|
||||
return tval
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self.energy_sp.put(value)
|
||||
|
||||
def is_moving(self):
|
||||
@@ -87,18 +87,18 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
return not bool(inmotion)
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
if not self.is_moving():
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
else:
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
self._currentChange = self.set_target_value(value+startvalue,*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
self._currentChange = self.set_target_value(value + startvalue, *args, **kwargs)
|
||||
|
||||
def wait(self):
|
||||
self._currentChange.wait()
|
||||
@@ -107,18 +107,19 @@ class Double_Crystal_Mono_AramisMacro:
|
||||
s = "**Double crystal monochromator**\n\n"
|
||||
motors = "theta gap x roll1 roll2 pitch2".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self,motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
pvs = "energy_rbk".split()
|
||||
for pv in pvs:
|
||||
s+= " - %s = %.4f\n" %(pv, getattr(self,pv).value)
|
||||
s += " - %s = %.4f\n" % (pv, getattr(self, pv).value)
|
||||
return s
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
class EcolEnergy:
|
||||
def __init__(self,Id, val='SARCL02-MBND100:P-SET', rb='SARCL02-MBND100:P-READ', dmov='SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK'):
|
||||
|
||||
def __init__(self, Id, val="SARCL02-MBND100:P-SET", rb="SARCL02-MBND100:P-READ", dmov="SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK"):
|
||||
self.Id = Id
|
||||
self.setter = PV(val)
|
||||
self.readback = PV(rb)
|
||||
@@ -128,15 +129,15 @@ class EcolEnergy:
|
||||
def get_current_value(self):
|
||||
return self.readback.get()
|
||||
|
||||
def move_and_wait(self, value, checktime=.01, precision=2):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=2):
|
||||
curr = self.setter.get()
|
||||
while abs(curr-value)>0.1:
|
||||
while abs(curr - value) > 0.1:
|
||||
curr = self.setter.get()
|
||||
self.setter.put(curr + np.sign(value-curr)*.1)
|
||||
self.setter.put(curr + np.sign(value - curr) * 0.1)
|
||||
sleep(0.3)
|
||||
|
||||
self.setter.put(value)
|
||||
while abs(self.get_current_value() - value)>precision:
|
||||
while abs(self.get_current_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
while not self.dmov.get():
|
||||
#print(self.dmov.get())
|
||||
@@ -147,38 +148,38 @@ class EcolEnergy:
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
|
||||
class Double_Crystal_Mono:
|
||||
def __init__(self, Id, timeAdjustable=None, timeReferenceEnergy=None, timeReference=None):
|
||||
self.Id = Id
|
||||
self.theta = Motor(Id + ':RX12')
|
||||
self.x = Motor(Id + ':TX12')
|
||||
self.gap = Motor(Id + ':T2')
|
||||
self.roll1 = Motor(Id + ':RZ1')
|
||||
self.roll2 = Motor(Id + ':RZ2')
|
||||
self.pitch2 = Motor(Id + ':RX2')
|
||||
|
||||
self.energy_rbk = PV(Id + ':ENERGY')
|
||||
self.energy_sp = PV(Id + ':ENERGY_SP')
|
||||
self.moving = PV(Id + ':MOVING')
|
||||
self._stop = PV(Id +':STOP.PROC')
|
||||
self.crystal_type = EnumWrapper(Id + ':CRYSTAL_SP')
|
||||
self.beam_offset = PV(Id + ':BEAM_OFFSET')
|
||||
self.timeAdjustable = timeAdjustable
|
||||
self.timeReferenceEnergy = timeReferenceEnergy
|
||||
self.timeReference = timeReference
|
||||
self.correctTime = False
|
||||
|
||||
def __init__(self, Id, timeAdjustable=None, timeReferenceEnergy=None, timeReference=None):
|
||||
self.Id = Id
|
||||
self.theta = Motor(Id + ":RX12")
|
||||
self.x = Motor(Id + ":TX12")
|
||||
self.gap = Motor(Id + ":T2")
|
||||
self.roll1 = Motor(Id + ":RZ1")
|
||||
self.roll2 = Motor(Id + ":RZ2")
|
||||
self.pitch2 = Motor(Id + ":RX2")
|
||||
|
||||
self.energy_rbk = PV(Id + ":ENERGY")
|
||||
self.energy_sp = PV(Id + ":ENERGY_SP")
|
||||
self.moving = PV(Id + ":MOVING")
|
||||
self._stop = PV(Id + ":STOP.PROC")
|
||||
self.crystal_type = EnumWrapper(Id + ":CRYSTAL_SP")
|
||||
self.beam_offset = PV(Id + ":BEAM_OFFSET")
|
||||
self.timeAdjustable = timeAdjustable
|
||||
self.timeReferenceEnergy = timeReferenceEnergy
|
||||
self.timeReference = timeReference
|
||||
self.correctTime = False
|
||||
|
||||
def _calcOffsetDetour(self, E, crystal_type=None, beam_offset=None):
|
||||
if not crystal_type:
|
||||
crystal_type = str(self.crystal_type)
|
||||
if crystal_type=="Si-111":
|
||||
if crystal_type == "Si-111":
|
||||
d = 3.1356124059796264
|
||||
else:
|
||||
raise NotImplementedError
|
||||
if not beam_offset:
|
||||
beam_offset = self.beam_offset.get()
|
||||
theta = np.arcsin(12398.419739640718/E/2/d)
|
||||
theta = np.arcsin(12398.419739640718 / E / 2 / d)
|
||||
return np.tan(theta) * beam_offset
|
||||
|
||||
def setTimeReference(self, t=None, E=None):
|
||||
@@ -190,16 +191,16 @@ class Double_Crystal_Mono:
|
||||
self.timeReference = t
|
||||
self.timeReferenceEnergy = E
|
||||
|
||||
def move_and_wait(self, value, checktime=.01, precision=.5):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=0.5):
|
||||
if self.correctTime:
|
||||
p_ref = self._calcOffsetDetour(self.timeReferenceEnergy)
|
||||
p_target = self._calcOffsetDetour(value)
|
||||
t_delta = (p_target-p_ref)*1e-3/299792458.
|
||||
t_delta = (p_target - p_ref) * 1e-3 / 299792458.0
|
||||
t_new = self.timeReference - t_delta
|
||||
print(f'correcting laser to xray timing delay by\nDt = {-t_delta} s to {t_new} s')
|
||||
print(f"correcting laser to xray timing delay by\nDt = {-t_delta} s to {t_new} s")
|
||||
time_mover = self.timeAdjustable.set_target_value(t_new)
|
||||
self.energy_sp.put(value)
|
||||
while abs(self.wait_for_valid_value()-value)>precision:
|
||||
while abs(self.wait_for_valid_value() - value) > precision:
|
||||
sleep(checktime)
|
||||
if self.correctTime:
|
||||
time_mover.wait()
|
||||
@@ -219,9 +220,9 @@ class Double_Crystal_Mono:
|
||||
tval = np.nan
|
||||
while not np.isfinite(tval):
|
||||
tval = self.energy_rbk.get()
|
||||
return(tval)
|
||||
return tval
|
||||
|
||||
def set_current_value(self,value):
|
||||
def set_current_value(self, value):
|
||||
self.energy_sp.put(value)
|
||||
|
||||
def is_moving(self):
|
||||
@@ -229,18 +230,18 @@ class Double_Crystal_Mono:
|
||||
return not bool(inmotion)
|
||||
|
||||
# spec-inspired convenience methods
|
||||
def mv(self,value):
|
||||
def mv(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
def wm(self,*args,**kwargs):
|
||||
return self.get_current_value(*args,**kwargs)
|
||||
def wm(self, *args, **kwargs):
|
||||
return self.get_current_value(*args, **kwargs)
|
||||
|
||||
def mvr(self,value,*args,**kwargs):
|
||||
def mvr(self, value, *args, **kwargs):
|
||||
if not self.is_moving():
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
else:
|
||||
startvalue = self.get_current_value(*args,**kwargs)
|
||||
self._currentChange = self.set_target_value(value+startvalue,*args,**kwargs)
|
||||
startvalue = self.get_current_value(*args, **kwargs)
|
||||
self._currentChange = self.set_target_value(value + startvalue, *args, **kwargs)
|
||||
|
||||
def wait(self):
|
||||
self._currentChange.wait()
|
||||
@@ -249,18 +250,19 @@ class Double_Crystal_Mono:
|
||||
s = "**Double crystal monochromator**\n\n"
|
||||
motors = "theta gap x roll1 roll2 pitch2".split()
|
||||
for motor in motors:
|
||||
s+= " - %s = %.4f\n" %(motor, getattr(self, motor).wm())
|
||||
s += " - %s = %.4f\n" % (motor, getattr(self, motor).wm())
|
||||
pvs = "energy_rbk".split()
|
||||
for pv in pvs:
|
||||
s+= " - %s = %.4f\n" %(pv, getattr(self, pv).value)
|
||||
s += " - %s = %.4f\n" % (pv, getattr(self, pv).value)
|
||||
return s
|
||||
|
||||
def __call__(self,value):
|
||||
def __call__(self, value):
|
||||
self._currentChange = self.set_target_value(value)
|
||||
|
||||
|
||||
class EcolEnergy:
|
||||
def __init__(self,Id, val='SARCL02-MBND100:P-SET', rb='SARCL02-MBND100:P-READ', dmov='SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK'):
|
||||
|
||||
def __init__(self, Id, val="SARCL02-MBND100:P-SET", rb="SARCL02-MBND100:P-READ", dmov="SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK"):
|
||||
self.Id = Id
|
||||
self.setter = PV(val)
|
||||
self.readback = PV(rb)
|
||||
@@ -270,11 +272,11 @@ class EcolEnergy:
|
||||
def get_current_value(self):
|
||||
return self.readback.get()
|
||||
|
||||
def move_and_wait(self, value, checktime=.01, precision=2):
|
||||
def move_and_wait(self, value, checktime=0.01, precision=2):
|
||||
curr = self.setter.get()
|
||||
while abs(curr-value)>0.1:
|
||||
while abs(curr - value) > 0.1:
|
||||
curr = self.setter.get()
|
||||
self.setter.put(curr + np.sign(value-curr)*.1)
|
||||
self.setter.put(curr + np.sign(value - curr) * 0.1)
|
||||
sleep(0.3)
|
||||
|
||||
self.setter.put(value)
|
||||
@@ -290,11 +292,12 @@ class EcolEnergy:
|
||||
|
||||
|
||||
class MonoEcolEnergy:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.name = 'energy_collimator'
|
||||
self.name = "energy_collimator"
|
||||
self.dcm = Double_Crystal_Mono(Id)
|
||||
self.ecol = EcolEnergy('ecol_dummy')
|
||||
self.ecol = EcolEnergy("ecol_dummy")
|
||||
self.offset = None
|
||||
self.MeVperEV = 0.78333
|
||||
|
||||
@@ -302,8 +305,7 @@ class MonoEcolEnergy:
|
||||
return self.dcm.get_current_value()
|
||||
|
||||
def move_and_wait(self, value):
|
||||
ch = [self.dcm.set_target_value(value),
|
||||
self.ecol.set_target_value(self.calcEcol(value))]
|
||||
ch = [self.dcm.set_target_value(value), self.ecol.set_target_value(self.calcEcol(value))]
|
||||
for tc in ch:
|
||||
tc.wait()
|
||||
|
||||
@@ -314,31 +316,32 @@ class MonoEcolEnergy:
|
||||
def alignOffsets(self):
|
||||
mrb = self.dcm.get_current_value()
|
||||
erb = self.ecol.get_current_value()
|
||||
self.offset = {'dcm':mrb, 'ecol':erb}
|
||||
self.offset = {"dcm": mrb, "ecol": erb}
|
||||
|
||||
def calcEcol(self, eV):
|
||||
return (eV-self.offset['dcm'])*self.MeVperEV + self.offset['ecol']
|
||||
return (eV - self.offset["dcm"]) * self.MeVperEV + self.offset["ecol"]
|
||||
|
||||
|
||||
class AlvraDCM_FEL:
|
||||
|
||||
def __init__(self, Id):
|
||||
self.Id = Id
|
||||
self.name = 'Alvra DCM monochromator coupled to FEL beam'
|
||||
self.name = "Alvra DCM monochromator coupled to FEL beam"
|
||||
# self.IOCstatus = PV('ALVRA:running') # bool 0 running, 1 not running
|
||||
self._FELcoupling = PV('SGE-OP2E-ARAMIS:MODE_SP') # string "Off" or "e-beam"
|
||||
self._setEnergy = PV('SAROP11-ARAMIS:ENERGY_SP_USER') # float eV
|
||||
self._getEnergy = PV('SAROP11-ARAMIS:ENERGY') # float eV
|
||||
self.ebeamEnergy = PV('SARCL02-MBND100:P-READ') # float MeV/c
|
||||
# self.ebeamEnergySP = PV('ALVRA:Energy_SP') # float MeV
|
||||
self.dcmStop = PV('SAROP11-ODCM105:STOP.PROC') # stop the DCM motors
|
||||
self.dcmMoving = PV('SAROP11-ODCM105:MOVING') # DCM moving field
|
||||
self._energyChanging = PV('SGE-OP2E-ARAMIS:MOVING') # PV telling you something related to the energy is changing
|
||||
self._alvraMode = PV('SAROP11-ARAMIS:MODE') # string Aramis SAROP11 mode
|
||||
self.ebeamOK = PV('SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK') # is ebeam no longer changing
|
||||
self.photCalib1 = PV('SGE-OP2E-ARAMIS:PH2E_X1') # photon energy calibration low calibration point
|
||||
self.photCalib2 = PV('SGE-OP2E-ARAMIS:PH2E_X2') # photon energy calibration high calibration point
|
||||
self.ebeamCalib1 = PV('SGE-OP2E-ARAMIS:PH2E_Y1') # electron energy calibration low calibration point
|
||||
self.ebeamCalib2 = PV('SGE-OP2E-ARAMIS:PH2E_Y2') # electron energy calibration high calibration point
|
||||
self._FELcoupling = PV("SGE-OP2E-ARAMIS:MODE_SP") # string "Off" or "e-beam"
|
||||
self._setEnergy = PV("SAROP11-ARAMIS:ENERGY_SP_USER") # float eV
|
||||
self._getEnergy = PV("SAROP11-ARAMIS:ENERGY") # float eV
|
||||
self.ebeamEnergy = PV("SARCL02-MBND100:P-READ") # float MeV/c
|
||||
# self.ebeamEnergySP = PV('ALVRA:Energy_SP') # float MeV
|
||||
self.dcmStop = PV("SAROP11-ODCM105:STOP.PROC") # stop the DCM motors
|
||||
self.dcmMoving = PV("SAROP11-ODCM105:MOVING") # DCM moving field
|
||||
self._energyChanging = PV("SGE-OP2E-ARAMIS:MOVING") # PV telling you something related to the energy is changing
|
||||
self._alvraMode = PV("SAROP11-ARAMIS:MODE") # string Aramis SAROP11 mode
|
||||
self.ebeamOK = PV("SFB_BEAM_ENERGY_ECOL:SUM-ERROR-OK") # is ebeam no longer changing
|
||||
self.photCalib1 = PV("SGE-OP2E-ARAMIS:PH2E_X1") # photon energy calibration low calibration point
|
||||
self.photCalib2 = PV("SGE-OP2E-ARAMIS:PH2E_X2") # photon energy calibration high calibration point
|
||||
self.ebeamCalib1 = PV("SGE-OP2E-ARAMIS:PH2E_Y1") # electron energy calibration low calibration point
|
||||
self.ebeamCalib2 = PV("SGE-OP2E-ARAMIS:PH2E_Y2") # electron energy calibration high calibration point
|
||||
|
||||
def __repr__(self):
|
||||
# ioc = self.IOCstatus.get()
|
||||
@@ -354,27 +357,27 @@ class AlvraDCM_FEL:
|
||||
photCalib2Str = self.photCalib2.get()
|
||||
ebeamCalib1Str = self.ebeamCalib1.get()
|
||||
ebeamCalib2Str = self.ebeamCalib2.get()
|
||||
|
||||
s = '**Alvra DCM-FEL status**\n\n'
|
||||
|
||||
s = "**Alvra DCM-FEL status**\n\n"
|
||||
# print('%s'%iocStr)
|
||||
# print('FEL coupling %s'%FELcouplingStr)
|
||||
# print('Alvra beamline mode %s'%alvraModeStr)
|
||||
# print('Photon energy (eV) %'%currEnergy)
|
||||
# s += '%s\n'%iocStr
|
||||
s += 'FEL coupling: %s\n'%FELcouplingStr
|
||||
s += 'Alvra beamline mode: %s\n'%alvraModeStr
|
||||
s += 'Photon energy: %.2f eV\n'%currEnergy
|
||||
s += 'Electron energy: %.2f MeV\n'%currebeamEnergy
|
||||
s += 'Calibration set points:\n'
|
||||
s += 'Low: Photon %.2f keV, Electron %.2f MeV\n'%(photCalib1Str, ebeamCalib1Str)
|
||||
s += 'High: Photon %.2f keV, Electron %.2f MeV\n'%(photCalib2Str, ebeamCalib2Str)
|
||||
s += "FEL coupling: %s\n" % FELcouplingStr
|
||||
s += "Alvra beamline mode: %s\n" % alvraModeStr
|
||||
s += "Photon energy: %.2f eV\n" % currEnergy
|
||||
s += "Electron energy: %.2f MeV\n" % currebeamEnergy
|
||||
s += "Calibration set points:\n"
|
||||
s += "Low: Photon %.2f keV, Electron %.2f MeV\n" % (photCalib1Str, ebeamCalib1Str)
|
||||
s += "High: Photon %.2f keV, Electron %.2f MeV\n" % (photCalib2Str, ebeamCalib2Str)
|
||||
return s
|
||||
|
||||
def get_current_value(self):
|
||||
return self._getEnergy.get()
|
||||
|
||||
def move_and_wait(self,value,checktime=.1,precision=0.5):
|
||||
self._FELcoupling.put(1) # ensure the FEL coupling is turned on
|
||||
def move_and_wait(self, value, checktime=0.1, precision=0.5):
|
||||
self._FELcoupling.put(1) # ensure the FEL coupling is turned on
|
||||
self._setEnergy.put(value)
|
||||
# while self.ebeamOK.get()==0:
|
||||
# sleep(checktime)
|
||||
@@ -385,7 +388,7 @@ class AlvraDCM_FEL:
|
||||
while self._energyChanging == 1:
|
||||
sleep(checktime)
|
||||
|
||||
def set_target_value(self,value,hold=False):
|
||||
def set_target_value(self, value, hold=False):
|
||||
changer = lambda: self.move_and_wait(value)
|
||||
return Task(changer, hold=hold)
|
||||
|
||||
|
||||
@@ -4,6 +4,7 @@ from ..aliases import Alias, append_object_to_object
|
||||
|
||||
|
||||
class RefLaser_Aramis:
|
||||
|
||||
def __init__(self, Id, elog=None, name=None, inpos=-18.818, outpos=-5):
|
||||
self.Id = Id
|
||||
self.elog = elog
|
||||
|
||||
Reference in New Issue
Block a user