diff --git a/ophyd_devices/epics/devices/eiger9m_csaxs.py b/ophyd_devices/epics/devices/eiger9m_csaxs.py index 46f7537..64fb266 100644 --- a/ophyd_devices/epics/devices/eiger9m_csaxs.py +++ b/ophyd_devices/epics/devices/eiger9m_csaxs.py @@ -28,7 +28,7 @@ class EigerError(Exception): class EigerTimeoutError(EigerError): - """Raised when the Eiger does not respond in time during unstage.""" + """Raised when the Eiger does not respond in time.""" pass @@ -156,8 +156,11 @@ class Eiger9MSetup(CustomDetectorMixin): self.std_client.stop_writer() def prepare_detector(self) -> None: - """Prepare detector for scan. - Includes checking the detector threshold, setting the acquisition parameters and setting the trigger source + """ + Prepare detector for scan + + Includes checking the detector threshold, setting the acquisition parameters + and setting the trigger source """ self.set_detector_threshold() self.set_acquisition_params() @@ -165,7 +168,7 @@ class Eiger9MSetup(CustomDetectorMixin): def set_detector_threshold(self) -> None: """ - Set correct detector threshold to 1/2 of current X-ray energy, allow 5% tolerance + Set correct detector threshold to 1/2 of the current X-ray energy, allow 5% tolerance Threshold might be in ev or keV """ @@ -275,6 +278,7 @@ class Eiger9MSetup(CustomDetectorMixin): ) def check_scanID(self) -> None: + """Checks if scanID has changed and stops the scan if it has""" old_scanID = self.parent.scaninfo.scanID self.parent.scaninfo.load_scan_metadata() if self.parent.scaninfo.scanID != old_scanID: @@ -339,7 +343,8 @@ class Eiger9MSetup(CustomDetectorMixin): class SLSDetectorCam(Device): - """SLS Detector Camera - Eiger 9M + """ + SLS Detector Camera - Eiger9M Base class to map EPICS PVs to ophyd signals. """ @@ -382,16 +387,15 @@ class DetectorState(enum.IntEnum): class Eiger9McSAXS(PSIDetectorBase): """ - Eiger 9M detector class for cSAXS + Eiger9M detector for CSAXS Parent class: PSIDetectorBase class attributes: - custom_prepare_cls (Eiger9MSetup): Custom detector setup class for cSAXS, - inherits from CustomDetectorMixin - cam (SLSDetectorCam): Detector camera - MIN_READOUT (float): Minimum readout time for the detector - + custom_prepare_cls (FalconSetup) : Custom detector setup class for cSAXS, + inherits from CustomDetectorMixin + PSIDetectorBase.set_min_readout (float) : Minimum readout time for the detector + Various EpicsPVs for controlling the detector """ # Specify which functions are revealed to the user in BEC client @@ -418,6 +422,12 @@ class Eiger9McSAXS(PSIDetectorBase): self.cam.trigger_mode.put(value) def stage(self) -> List[object]: + """ + Add functionality to stage, and arm the detector + + Additional call to: + - custom_prepare.arm_acquisition() + """ rtr = super().stage() self.custom_prepare.arm_acquisition() return rtr diff --git a/ophyd_devices/epics/devices/falcon_csaxs.py b/ophyd_devices/epics/devices/falcon_csaxs.py index 594314c..b81faf3 100644 --- a/ophyd_devices/epics/devices/falcon_csaxs.py +++ b/ophyd_devices/epics/devices/falcon_csaxs.py @@ -25,7 +25,7 @@ class FalconError(Exception): class FalconTimeoutError(FalconError): - """Raised when the Falcon does not respond in time during unstage.""" + """Raised when the Falcon does not respond in time.""" pass @@ -38,7 +38,8 @@ class DetectorState(enum.IntEnum): class TriggerSource(enum.IntEnum): - """Trigger source for Falcon detector + """ + Trigger source for Falcon detector Translates setttings for PV:pixel_advance_mode """ @@ -49,7 +50,8 @@ class TriggerSource(enum.IntEnum): class MappingSource(enum.IntEnum): - """Mapping source for Falcon detector + """ + Mapping source for Falcon detector Translates setttings for PV:collect_mode """ @@ -59,7 +61,8 @@ class MappingSource(enum.IntEnum): class EpicsDXPFalcon(Device): - """DXP parameters for Falcon detector + """ + DXP parameters for Falcon detector Base class to map EPICS PVs from DXP parameters to ophyd signals. """ @@ -83,7 +86,8 @@ class EpicsDXPFalcon(Device): class FalconHDF5Plugins(Device): - """HDF5 parameters for Falcon detector + """ + HDF5 parameters for Falcon detector Base class to map EPICS PVs from HDF5 Plugin to ophyd signals. """ @@ -103,7 +107,8 @@ class FalconHDF5Plugins(Device): class FalconSetup(CustomDetectorMixin): - """Falcon setup class for cSAXS + """ + Falcon setup class for cSAXS Parent class: CustomDetectorMixin @@ -113,9 +118,12 @@ class FalconSetup(CustomDetectorMixin): super().__init__(parent=parent, *args, **kwargs) def initialize_default_parameter(self) -> None: - """Set default parameters for Falcon + """ + Set default parameters for Falcon + readout (float): readout time in seconds _value_pixel_per_buffer (int): number of spectra in buffer of Falcon Sitoro + """ self.parent._value_pixel_per_buffer = 20 self.update_readout_time() @@ -218,7 +226,7 @@ class FalconSetup(CustomDetectorMixin): self.parent.hdf5.capture.put(1) def arm_acquisition(self) -> None: - """Arm Eiger detector for acquisition""" + """Arm detector for acquisition""" self.parent.start_all.put(1) signal_conditions = [ ( @@ -238,6 +246,7 @@ class FalconSetup(CustomDetectorMixin): ) def check_scanID(self) -> None: + """Checks if scanID has changed and stops the scan if it has""" old_scanID = self.parent.scaninfo.scanID self.parent.scaninfo.load_scan_metadata() if self.parent.scaninfo.scanID != old_scanID: @@ -273,9 +282,15 @@ class FalconSetup(CustomDetectorMixin): pipe.execute() def finished(self) -> None: - """Check if acquisition is finished. + """ + Check if acquisition is finished. - For the Falcon we accept that it misses a trigger since we can reconstruct it from the data. + In case of the Falcon Sitoro, we check if the number of triggers is equal to the number of written frames. + + In case this is not correct, we would NOT (!) raise an Error at this moment + because there is data to reassemble the pixels. + + However, this decision could be revoked and handled differently. """ signal_conditions = [ ( @@ -307,12 +322,13 @@ class FalconcSAXS(PSIDetectorBase): Parent class: PSIDetectorBase class attributes: - custom_prepare_cls (Eiger9MSetup) : Custom detector setup class for cSAXS, - inherits from CustomDetectorMixin - dxp (EpicsDXPFalcon) : DXP parameters for Falcon detector - mca (EpicsMCARecord) : MCA parameters for Falcon detector - hdf5 (FalconHDF5Plugins) : HDF5 parameters for Falcon detector - MIN_READOUT (float) : Minimum readout time for the detector + custom_prepare_cls (FalconSetup) : Custom detector setup class for cSAXS, + inherits from CustomDetectorMixin + PSIDetectorBase.set_min_readout (float) : Minimum readout time for the detector + dxp (EpicsDXPFalcon) : DXP parameters for Falcon detector + mca (EpicsMCARecord) : MCA parameters for Falcon detector + hdf5 (FalconHDF5Plugins) : HDF5 parameters for Falcon detector + MIN_READOUT (float) : Minimum readout time for the detector """ # Specify which functions are revealed to the user in BEC client @@ -370,6 +386,12 @@ class FalconcSAXS(PSIDetectorBase): self.ignore_gate.put(ignore_gate) def stage(self) -> List[object]: + """ + Add functionality to stage, and arm the detector + + Additional call to: + - custom_prepare.arm_acquisition() + """ rtr = super().stage() self.custom_prepare.arm_acquisition() return rtr diff --git a/ophyd_devices/epics/devices/pilatus_csaxs.py b/ophyd_devices/epics/devices/pilatus_csaxs.py index 433543f..db64898 100644 --- a/ophyd_devices/epics/devices/pilatus_csaxs.py +++ b/ophyd_devices/epics/devices/pilatus_csaxs.py @@ -153,6 +153,7 @@ class PilatusSetup(CustomDetectorMixin): os.makedirs(filepath, exist_ok=True) def stop_detector_backend(self) -> None: + """Stop the file writer zmq service for pilatus_2""" self.close_file_writer() time.sleep(0.1) self.stop_file_writer() @@ -260,7 +261,7 @@ class PilatusSetup(CustomDetectorMixin): time.sleep(0.1) logger.info(f"{res.status_code} -{res.text} - {res.content}") - # Sent requests.put to xbl-daq-34 to wait for data + # Send requests.put to xbl-daq-34 to wait for data url = "http://xbl-daq-34:8091/pilatus_2/wait" data_msg = [ "zmqWriter", @@ -313,12 +314,14 @@ class PilatusSetup(CustomDetectorMixin): For the pilatus detector, it is used to arm the detector for the acquisition, because the detector times out after ˜7-8 seconds without seeing a trigger. + """ self.arm_acquisition() def arm_acquisition(self) -> None: + """Arms the detector for the acquisition""" self.parent.cam.acquire.put(1) - # TODO Sleep needed, to be tested how long it is needed! + # TODO is this sleep needed? to be tested with detector and for how long time.sleep(0.5) def publish_file_location(self, done: bool = False, successful: bool = None) -> None: @@ -390,12 +393,17 @@ class PilatusSetup(CustomDetectorMixin): """Stop detector""" self.parent.cam.acquire.put(0) + def check_scanID(self) -> None: + """Checks if scanID has changed and stops the scan if it has""" + old_scanID = self.parent.scaninfo.scanID + self.parent.scaninfo.load_scan_metadata() + if self.parent.scaninfo.scanID != old_scanID: + self.parent._stopped = True + class PilatuscSAXS(PSIDetectorBase): """Pilatus_2 300k detector for CSAXS - Eiger 9M detector class for cSAXS - Parent class: PSIDetectorBase class attributes: