class DodgyEpicsScaler(Device):
    '''SynApps Scaler Record interface'''

    # tigger + trigger mode
    count = C(DodgyEpicsSignal, '.CNT', trigger_value=1)
    count_mode = C(DodgyEpicsSignal, '.CONT', string=True)

    # delay from triggering to starting counting
    delay = C(DodgyEpicsSignal, '.DLY')
    auto_count_delay = C(DodgyEpicsSignal, '.DLY1')

    # the data
    channels = DDC(_scaler_fields(DodgyEpicsSignal, 'chan', '.S', range(1,
                                                                        33)))
    names = DDC(_scaler_fields(DodgyEpicsSignal, 'name', '.NM', range(1, 33)))

    time = C(DodgyEpicsSignal, '.T')
    freq = C(DodgyEpicsSignal, '.FREQ')

    preset_time = C(DodgyEpicsSignal, '.TP')
    auto_count_time = C(DodgyEpicsSignal, '.TP1')

    presets = DDC(
        _scaler_fields(DodgyEpicsSignal, 'preset', '.PR', range(1, 33)))
    gates = DDC(_scaler_fields(DodgyEpicsSignal, 'gate', '.G', range(1, 33)))

    update_rate = C(DodgyEpicsSignal, '.RATE')
    auto_count_update_rate = C(DodgyEpicsSignal, '.RAT1')

    egu = C(DodgyEpicsSignal, '.EGU')

    def __init__(self,
                 prefix,
                 *,
                 read_attrs=None,
                 configuration_attrs=None,
                 name=None,
                 parent=None,
                 **kwargs):
        if read_attrs is None:
            read_attrs = ['channels', 'time']

        if configuration_attrs is None:
            configuration_attrs = [
                'preset_time', 'presets', 'gates', 'names', 'freq',
                'auto_count_time', 'count_mode', 'delay', 'auto_count_delay',
                'egu'
            ]

        super().__init__(prefix,
                         read_attrs=read_attrs,
                         configuration_attrs=configuration_attrs,
                         name=name,
                         parent=parent,
                         **kwargs)

        self.stage_sigs.update([('count_mode', 0)])

        for channel in ['channels.chan2', 'channels.chan3', 'channels.chan4']:
            getattr(self, channel).kind = 'hinted'
예제 #2
0
class EpicsSwaitRecord(Device):
    """synApps swait record: used as $(P):userCalc$(N)"""
    desc = Cpt(EpicsSignal, '.DESC')
    scan = Cpt(EpicsSignal, '.SCAN')
    calc = Cpt(EpicsSignal, '.CALC')
    val = Cpt(EpicsSignalRO, '.VAL')
    prec = Cpt(EpicsSignal, '.PREC')
    oevt = Cpt(EpicsSignal, '.OEVT')
    outn = Cpt(EpicsSignal, '.OUTN')
    odly = Cpt(EpicsSignal, '.ODLY')
    doln = Cpt(EpicsSignal, '.DOLN')
    dold = Cpt(EpicsSignal, '.DOLD')
    dopt = Cpt(EpicsSignal, '.DOPT')
    oopt = Cpt(EpicsSignal, '.OOPT')
    flnk = Cpt(EpicsSignal, '.FLNK')

    channels = DDC(_swait_channels("A B C D E F G H I J K L".split()))

    def reset(self):
        """set all fields to default values"""
        self.desc.put(self.desc.pvname.split(".")[0])
        self.scan.put("Passive")
        self.calc.put("0")
        self.prec.put("5")
        self.dold.put(0)
        self.doln.put("")
        self.dopt.put("Use VAL")
        self.flnk.put("0")
        self.odly.put(0)
        self.oopt.put("Every Time")
        self.outn.put("")
        for letter in self.channels.read_attrs:
            channel = self.channels.__getattr__(letter)
            channel.reset()
예제 #3
0
class ScalerMCA(Device):
    _default_read_attrs = ('channels', 'current_channel')
    _default_configuration_attrs = ('nuse', 'prescale')

    channels = DDC(
        {f'mca{k:02d}': (EpicsSignal, f"mca{k}", {})
         for k in range(1, 33)})
    startall = C(EpicsSignal, 'StartAll', string=True)
    stopall = C(EpicsSignal, 'StopAll', string=True)
    eraseall = C(EpicsSignal, 'EraseAll', string=True)
    erasestart = C(EpicsSignal, 'EraseStart', string=True)

    current_channel = C(EpicsSignal, 'CurrentChannel')
    nuse = C(EpicsSignal, 'NuseAll')
    prescale = C(EpicsSignal, 'Prescale')

    # high is acquiring
    status = C(EpicsSignal, 'Acquiring', string=True)

    def stage(self):
        super().stage()
        self.eraseall.put('Erase')

    def stop(self):
        self.stopall.put('Stop')

    def trigger(self):
        self.erasestart.put('Erase')

        return StatusBase()
예제 #4
0
class SwaitRecord(EpicsRecordDeviceCommonAll):
    """
    synApps swait record: used as $(P):userCalc$(N)

    .. autosummary::
       
        ~reset

    """
    precision = Cpt(EpicsSignal, ".PREC")
    high_operating_range = Cpt(EpicsSignal, ".HOPR")
    low_operating_range = Cpt(EpicsSignal, ".LOPR")

    calculated_value = Cpt(EpicsSignal, ".VAL")
    calculation = Cpt(EpicsSignal, ".CALC")

    output_link_pv = Cpt(EpicsSignal, '.OUTN')
    output_location_name = Cpt(EpicsSignal, '.DOLN')
    output_location_data = Cpt(EpicsSignal, '.DOLD')
    output_data_option = Cpt(EpicsSignal, ".DOPT")

    output_execute_option = Cpt(EpicsSignal, ".OOPT")
    output_execution_delay = Cpt(EpicsSignal, ".ODLY")
    event_to_issue = Cpt(EpicsSignal, ".OEVT")

    read_attrs = APS_utils.itemizer("channels.%s", CHANNEL_LETTERS_LIST)
    hints = {'fields': read_attrs}
    
    channels = DDC(_swait_channels(CHANNEL_LETTERS_LIST))

    @property
    def value(self):
        return self.calculated_value.value
    
    def reset(self):
        """set all fields to default values"""
        pvname = self.description.pvname.split(".")[0]
        self.description.put(pvname)
        self.scanning_rate.put("Passive")
        self.calculation.put("0")
        self.precision.put("5")
        self.output_location_data.put(0)
        self.output_location_name.put("")
        self.output_data_option.put("Use VAL")
        self.forward_link.put("0")
        self.output_execution_delay.put(0)
        self.output_execute_option.put("Every Time")
        self.output_link_pv.put("")
        for letter in self.channels.read_attrs:
            channel = getattr(self.channels, letter)
            if isinstance(channel, SwaitRecordChannel):
                channel.reset()

        self.read_attrs = ["channels.%s" % c for c in CHANNEL_LETTERS_LIST]
        self.hints = {'fields': self.read_attrs}

        self.read_attrs.append('calculated_value')
예제 #5
0
파일: swait.py 프로젝트: mrakitin/apstools
class swaitRecord(Device):
    """
    synApps swait record: used as $(P):userCalc$(N)

    .. autosummary::
       
        ~reset

    """
    desc = Cpt(EpicsSignal, '.DESC')
    scan = Cpt(EpicsSignal, '.SCAN')
    calc = Cpt(EpicsSignal, '.CALC')
    val = Cpt(EpicsSignalRO, '.VAL')
    prec = Cpt(EpicsSignal, '.PREC')
    process = Cpt(EpicsSignal, '.PROC')
    oevt = Cpt(EpicsSignal, '.OEVT')
    outn = Cpt(EpicsSignal, '.OUTN')
    odly = Cpt(EpicsSignal, '.ODLY')
    doln = Cpt(EpicsSignal, '.DOLN')
    dold = Cpt(EpicsSignal, '.DOLD')
    dopt = Cpt(EpicsSignal, '.DOPT')
    oopt = Cpt(EpicsSignal, '.OOPT')
    flnk = Cpt(EpicsSignal, '.FLNK')

    hints = {
        'fields':
        ["channels.%s" % c for c in "A B C D E F G H I J K L".split()]
    }
    read_attrs = ["channels.%s" % c for c in "A B C D E F G H I J K L".split()]

    channels = DDC(_swait_channels("A B C D E F G H I J K L".split()))

    def reset(self):
        """set all fields to default values"""
        self.desc.put(self.desc.pvname.split(".")[0])
        self.scan.put("Passive")
        self.calc.put("0")
        self.prec.put("5")
        self.dold.put(0)
        self.doln.put("")
        self.dopt.put("Use VAL")
        self.flnk.put("0")
        self.odly.put(0)
        self.oopt.put("Every Time")
        self.outn.put("")
        for letter in self.channels.read_attrs:
            channel = getattr(self.channels, letter)
            if isinstance(channel, swaitRecordChannel):
                channel.reset()
        self.hints = {
            'fields':
            ["channels.%s" % c for c in "A B C D E F G H I J K L".split()]
        }
        self.read_attrs = [
            "channels.%s" % c for c in "A B C D E F G H I J K L".split()
        ]
        self.read_attrs.append('val')
예제 #6
0
class AttenuatorCalculator_AT2L0(AttenuatorCalculatorBase):
    """
    Solid attenuator variant from the LCLS-II XTES project.

    Parameters
    ----------
    prefix : str
        Full Solid Attenuator base PV.

    name : str
        Alias for the Solid Attenuator.
    """

    tab_component_names = True
    first_filter = 2
    num_filters = 18
    # "filters" DDC holds all the individual components:
    _filter_parent = 'filters'
    _filter_index_to_attr = {
        idx: f'filter_{idx:02d}' for idx in range(first_filter,
                                                  num_filters + first_filter)
    }

    # Creates filters from 2 to num_filters, with attributes filter_02 and so
    # on.
    filters = DDC(
        {attr: (AttenuatorCalculatorFilter,
                f':FILTER:{idx:02d}:',
                {'index': idx})
         for idx, attr in _filter_index_to_attr.items()
         }
    )

    def format_status_info(self, status_info):
        """
        Override status info handler to render the attenuator.
        """
        table = utils.format_status_table(
            status_info.get('filters', {}),
            row_to_key=self._filter_index_to_attr,
            column_to_key={
                'Active': 'active',
                'Material': 'material',
                'Thickness [um]': 'thickness',
                'Stuck': 'is_stuck',
                'Transmission': 'transmission',
                'Transmission 3 Omega': 'transmission_3omega',
            },
            row_identifier='Filter',
        )

        return str(table)
예제 #7
0
class EpicsScaler(Device):
    '''SynApps Scaler Record interface'''
    _default_configuration_attrs = ('preset_time', 'presets', 'gates', 'names',
                                    'freq', 'auto_count_time', 'count_mode',
                                    'delay', 'auto_count_delay', 'egu')
    _default_read_attrs = ('channels', 'time')
    # tigger + trigger mode
    count = C(EpicsSignal, '.CNT', trigger_value=1)
    count_mode = C(EpicsSignal, '.CONT', string=True)

    # delay from triggering to starting counting
    delay = C(EpicsSignal, '.DLY')
    auto_count_delay = C(EpicsSignal, '.DLY1')

    # the data
    channels = DDC(_scaler_fields(EpicsSignalRO, 'chan', '.S', range(1, 33)))
    names = DDC(_scaler_fields(EpicsSignal, 'name', '.NM', range(1, 33)))

    time = C(EpicsSignal, '.T')
    freq = C(EpicsSignal, '.FREQ')

    preset_time = C(EpicsSignal, '.TP')
    auto_count_time = C(EpicsSignal, '.TP1')

    presets = DDC(_scaler_fields(EpicsSignal, 'preset', '.PR', range(1, 33)))
    gates = DDC(_scaler_fields(EpicsSignal, 'gate', '.G', range(1, 33)))

    update_rate = C(EpicsSignal, '.RATE')
    auto_count_update_rate = C(EpicsSignal, '.RAT1')

    egu = C(EpicsSignal, '.EGU')

    def __init__(self, *args, **kwargs):

        super().__init__(*args, **kwargs)

        self.stage_sigs.update([('count_mode', 0)])
예제 #8
0
class SRXScaler(EpicsScaler):
    acquire_mode = Cpt(EpicsSignal, 'AcquireMode')
    acquiring = Cpt(EpicsSignal, 'Acquiring')
    asyn = Cpt(EpicsSignal, 'Asyn')
    channel1_source = Cpt(EpicsSignal, 'Channel1Source')
    channel_advance = Cpt(EpicsSignal, 'ChannelAdvance', string=True)
    channels = DDC(_scaler_fields('chan', '.S', range(1, 33)))
    client_wait = Cpt(EpicsSignal, 'ClientWait')
    count_on_start = Cpt(EpicsSignal, 'CountOnStart')
    current_channel = Cpt(EpicsSignal, 'CurrentChannel')
    disable_auto_count = Cpt(EpicsSignal, 'DisableAutoCount')
    do_read_all = Cpt(EpicsSignal, 'DoReadAll')
    dwell = Cpt(EpicsSignal, 'Dwell')
    elapsed_real = Cpt(EpicsSignal, 'ElapsedReal')
    enable_client_wait = Cpt(EpicsSignal, 'EnableClientWait')
    erase_all = Cpt(EpicsSignal, 'EraseAll')
    erase_start = Cpt(EpicsSignal, 'EraseStart')
    firmware = Cpt(EpicsSignal, 'Firmware')
    hardware_acquiring = Cpt(EpicsSignal, 'HardwareAcquiring')
    input_mode = Cpt(EpicsSignal, 'InputMode')
    max_channels = Cpt(EpicsSignal, 'MaxChannels')
    model = Cpt(EpicsSignal, 'Model')
    mux_output = Cpt(EpicsSignal, 'MUXOutput')
    nuse_all = Cpt(EpicsSignal, 'NuseAll')
    output_mode = Cpt(EpicsSignal, 'OutputMode')
    output_polarity = Cpt(EpicsSignal, 'OutputPolarity')
    prescale = Cpt(EpicsSignal, 'Prescale')
    preset_real = Cpt(EpicsSignal, 'PresetReal')
    read_all = Cpt(EpicsSignal, 'ReadAll')
    read_all_once = Cpt(EpicsSignal, 'ReadAllOnce')
    set_acquiring = Cpt(EpicsSignal, 'SetAcquiring')
    set_client_wait = Cpt(EpicsSignal, 'SetClientWait')
    snl_connected = Cpt(EpicsSignal, 'SNL_Connected')
    software_channel_advance = Cpt(EpicsSignal, 'SoftwareChannelAdvance')
    count_mode = Cpt(EpicsSignal, '.CONT')
    start_all = Cpt(EpicsSignal, 'StartAll')
    stop_all = Cpt(EpicsSignal, 'StopAll')
    user_led = Cpt(EpicsSignal, 'UserLED')
    wfrm = Cpt(EpicsSignal, 'Wfrm')
    mca1 = Cpt(EpicsSignalRO, 'mca1')
    mca2 = Cpt(EpicsSignalRO, 'mca2')
    mca3 = Cpt(EpicsSignalRO, 'mca3')
    mca4 = Cpt(EpicsSignalRO, 'mca4')

    def __init__(self, prefix, **kwargs):
        super().__init__(prefix, **kwargs)
        self.stage_sigs[self.count_mode] = 'OneShot'
예제 #9
0
class SRXScaler(EpicsScaler):
    acquire_mode = Cpt(EpicsSignal, "AcquireMode")
    acquiring = Cpt(EpicsSignal, "Acquiring")
    asyn = Cpt(EpicsSignal, "Asyn")
    channel1_source = Cpt(EpicsSignal, "Channel1Source")
    channel_advance = Cpt(EpicsSignal, "ChannelAdvance", string=True)
    channels = DDC(_scaler_fields("chan", ".S", range(1, 33)))
    client_wait = Cpt(EpicsSignal, "ClientWait")
    count_on_start = Cpt(EpicsSignal, "CountOnStart")
    current_channel = Cpt(EpicsSignal, "CurrentChannel")
    disable_auto_count = Cpt(EpicsSignal, "DisableAutoCount")
    do_read_all = Cpt(EpicsSignal, "DoReadAll")
    dwell = Cpt(EpicsSignal, "Dwell")
    elapsed_real = Cpt(EpicsSignal, "ElapsedReal")
    enable_client_wait = Cpt(EpicsSignal, "EnableClientWait")
    erase_all = Cpt(EpicsSignal, "EraseAll")
    erase_start = Cpt(EpicsSignal, "EraseStart")
    firmware = Cpt(EpicsSignal, "Firmware")
    hardware_acquiring = Cpt(EpicsSignal, "HardwareAcquiring")
    input_mode = Cpt(EpicsSignal, "InputMode")
    max_channels = Cpt(EpicsSignal, "MaxChannels")
    model = Cpt(EpicsSignal, "Model")
    mux_output = Cpt(EpicsSignal, "MUXOutput")
    nuse_all = Cpt(EpicsSignal, "NuseAll")
    output_mode = Cpt(EpicsSignal, "OutputMode")
    output_polarity = Cpt(EpicsSignal, "OutputPolarity")
    prescale = Cpt(EpicsSignal, "Prescale")
    preset_real = Cpt(EpicsSignal, "PresetReal")
    read_all = Cpt(EpicsSignal, "ReadAll")
    read_all_once = Cpt(EpicsSignal, "ReadAllOnce")
    set_acquiring = Cpt(EpicsSignal, "SetAcquiring")
    set_client_wait = Cpt(EpicsSignal, "SetClientWait")
    snl_connected = Cpt(EpicsSignal, "SNL_Connected")
    software_channel_advance = Cpt(EpicsSignal, "SoftwareChannelAdvance")
    count_mode = Cpt(EpicsSignal, ".CONT")
    start_all = Cpt(EpicsSignal, "StartAll")
    stop_all = Cpt(EpicsSignal, "StopAll")
    user_led = Cpt(EpicsSignal, "UserLED")
    wfrm = Cpt(EpicsSignal, "Wfrm")
    mca1 = Cpt(EpicsSignalRO, "mca1")
    mca2 = Cpt(EpicsSignalRO, "mca2")
    mca3 = Cpt(EpicsSignalRO, "mca3")
    mca4 = Cpt(EpicsSignalRO, "mca4")

    def __init__(self, prefix, **kwargs):
        super().__init__(prefix, **kwargs)
        self.stage_sigs[self.count_mode] = "OneShot"
예제 #10
0
class TransformRecord(EpicsRecordDeviceCommonAll):
    """
    EPICS transform record support in ophyd

	.. autosummary::
	   
		~reset
    
    :see: https://htmlpreview.github.io/?https://raw.githubusercontent.com/epics-modules/calc/R3-6-1/documentation/TransformRecord.html#Fields
    """
    units = Cpt(EpicsSignal, ".EGU")
    precision = Cpt(EpicsSignal, ".PREC")
    version = Cpt(EpicsSignalRO, ".VERS")

    calc_option = Cpt(EpicsSignal, ".COPT")
    invalid_link_action = Cpt(EpicsSignalRO, ".IVLA")
    input_bitmap = Cpt(EpicsSignalRO, ".MAP")

    read_attrs = APS_utils.itemizer("channels.%s", CHANNEL_LETTERS_LIST)
    hints = {'fields': read_attrs}

    channels = DDC(_channels(CHANNEL_LETTERS_LIST))

    def reset(self):
        """set all fields to default values"""
        self.scanning_rate.put("Passive")
        self.description.put(self.description.pvname.split(".")[0])
        self.units.put("")
        self.calc_option.put(0)
        self.precision.put("3")
        self.forward_link.put("")
        for letter in self.channels.read_attrs:
            channel = getattr(self.channels, letter)
            if isinstance(channel, transformRecordChannel):
                channel.reset()
        self.hints = {
            'fields': ["channels.%s" % c for c in CHANNEL_LETTERS_LIST]
        }
        self.read_attrs = ["channels.%s" % c for c in CHANNEL_LETTERS_LIST]
예제 #11
0
class ScalerMCA(Device):
    _default_read_attrs = ('channels', 'current_channel')
    _default_configuration_attrs = ('nuse', 'prescale')

    # things to be read as data
    channels = DDC({f'mca{k:02d}': (EpicsSignal, f"mca{k}", {})
                    for k in range(1, 21)})
    current_channel = C(EpicsSignal, 'CurrentChannel')
    # configuration details
    nuse = C(EpicsSignal, 'NuseAll', kind='config')
    prescale = C(EpicsSignal, 'Prescale', kind='config')
    channel_advance = C(EpicsSignal, 'ChannelAdvance')
    
    # control PVs

    # high is acquiring
    with kind_context('omitted') as Co:
        status = Co(EpicsSignal, 'Acquiring', string=True,)
        startall = Co(EpicsSignal, 'StartAll', string=True)
        stopall = Co(EpicsSignal, 'StopAll', string=True)
        eraseall = Co(EpicsSignal, 'EraseAll', string=True)
        erasestart = Co(EpicsSignal, 'EraseStart', string=True)

    def stage(self):
        super().stage()
        self.eraseall.put('Erase')

    def stop(self):
        self.stopall.put('Stop')

    def trigger(self):
        self.erasestart.put('Erase')

        return StatusBase(done=True, success=True)

    def read(self):
        # TODO handle file writing and document generation
        return super().read()
예제 #12
0
class ScalerMCA(Device):
    _default_read_attrs = ("channels", "current_channel")
    _default_configuration_attrs = ("nuse", "prescale")

    # things to be read as data
    channels = DDC({f"mca{k:02d}": (EpicsSignal, f"mca{k}", {}) for k in range(1, 21)})
    current_channel = C(EpicsSignal, "CurrentChannel")
    # configuration details
    nuse = C(EpicsSignal, "NuseAll", kind="config")
    prescale = C(EpicsSignal, "Prescale", kind="config")
    channel_advance = C(EpicsSignal, "ChannelAdvance")

    # control PVs

    # high is acquiring
    with kind_context("omitted") as Co:
        status = Co(EpicsSignal, "Acquiring", string=True)
        startall = Co(EpicsSignal, "StartAll", string=True)
        stopall = Co(EpicsSignal, "StopAll", string=True)
        eraseall = Co(EpicsSignal, "EraseAll", string=True)
        erasestart = Co(EpicsSignal, "EraseStart", string=True)

    def stage(self):
        staged_cmpts = super().stage()
        self.eraseall.put("Erase")
        return staged_cmpts

    def stop(self):
        self.stopall.put("Stop")

    def trigger(self):
        self.erasestart.put("Erase")

        return StatusBase(done=True, success=True)

    def read(self):
        # TODO handle file writing and document generation
        return super().read()
예제 #13
0
class swaitRecord(Device):
    """synApps swait record: used as $(P):userCalc$(N)"""
    desc = Cpt(EpicsSignal, '.DESC')
    scan = Cpt(EpicsSignal, '.SCAN')
    calc = Cpt(EpicsSignal, '.CALC')
    val = Cpt(EpicsSignalRO, '.VAL')
    prec = Cpt(EpicsSignal, '.PREC')
    oevt = Cpt(EpicsSignal, '.OEVT')
    outn = Cpt(EpicsSignal, '.OUTN')
    odly = Cpt(EpicsSignal, '.ODLY')
    doln = Cpt(EpicsSignal, '.DOLN')
    dold = Cpt(EpicsSignal, '.DOLD')
    dopt = Cpt(EpicsSignal, '.DOPT')
    oopt = Cpt(EpicsSignal, '.OOPT')
    flnk = Cpt(EpicsSignal, '.FLNK')

    _channel_letters = "A B C D E F G H I J K L".split()
    # TODO: eliminate the ".channels"
    # Note that the scaler support has this also.
    channels = DDC(_swait_channels('chan', _channel_letters))

    def reset(self):
        """set all fields to default values"""
        self.scan.put("Passive")
        self.calc.put("0")
        self.prec.put("5")
        self.dold.put(0)
        self.doln.put("")
        self.dopt.put("Use VAL")
        self.flnk.put("0")
        self.odly.put(0)
        self.oopt.put("Every Time")
        self.outn.put("")
        for letter in self.channels.read_attrs:
            channel = self.channels.__getattr__(letter)
            channel.value.put(0)
            channel.input_pv.put("")
            channel.input_trigger.put("Yes")
예제 #14
0
class StatsPluginCSX(PluginBase):
    """This supports changes to time series PV names in AD 3-3

    Due to https://github.com/areaDetector/ADCore/pull/333
    """
    _default_suffix = 'Stats1:'
    _suffix_re = 'Stats\d:'
    _html_docs = ['NDPluginStats.html']
    _plugin_type = 'NDPluginStats'

    _default_configuration_attrs = (
        PluginBase._default_configuration_attrs +
        ('centroid_threshold', 'compute_centroid', 'compute_histogram',
         'compute_profiles', 'compute_statistics', 'bgd_width', 'hist_size',
         'hist_min', 'hist_max', 'profile_size', 'profile_cursor'))

    bgd_width = ADCpt(SignalWithRBV, 'BgdWidth')
    centroid_threshold = ADCpt(SignalWithRBV, 'CentroidThreshold')

    centroid = DDC(ad_group(EpicsSignalRO,
                            (('x', 'CentroidX_RBV'), ('y', 'CentroidY_RBV'))),
                   doc='The centroid XY',
                   default_read_attrs=('x', 'y'))

    compute_centroid = ADCpt(SignalWithRBV, 'ComputeCentroid', string=True)
    compute_histogram = ADCpt(SignalWithRBV, 'ComputeHistogram', string=True)
    compute_profiles = ADCpt(SignalWithRBV, 'ComputeProfiles', string=True)
    compute_statistics = ADCpt(SignalWithRBV, 'ComputeStatistics', string=True)

    cursor = DDC(ad_group(SignalWithRBV, (('x', 'CursorX'), ('y', 'CursorY'))),
                 doc='The cursor XY',
                 default_read_attrs=('x', 'y'))

    hist_entropy = ADCpt(EpicsSignalRO, 'HistEntropy_RBV')
    hist_max = ADCpt(SignalWithRBV, 'HistMax')
    hist_min = ADCpt(SignalWithRBV, 'HistMin')
    hist_size = ADCpt(SignalWithRBV, 'HistSize')
    histogram = ADCpt(EpicsSignalRO, 'Histogram_RBV')

    max_size = DDC(ad_group(EpicsSignal,
                            (('x', 'MaxSizeX'), ('y', 'MaxSizeY'))),
                   doc='The maximum size in XY',
                   default_read_attrs=('x', 'y'))

    max_value = ADCpt(EpicsSignalRO, 'MaxValue_RBV')
    max_xy = DDC(ad_group(EpicsSignalRO,
                          (('x', 'MaxX_RBV'), ('y', 'MaxY_RBV'))),
                 doc='Maximum in XY',
                 default_read_attrs=('x', 'y'))

    mean_value = ADCpt(EpicsSignalRO, 'MeanValue_RBV')
    min_value = ADCpt(EpicsSignalRO, 'MinValue_RBV')

    min_xy = DDC(ad_group(EpicsSignalRO,
                          (('x', 'MinX_RBV'), ('y', 'MinY_RBV'))),
                 doc='Minimum in XY',
                 default_read_attrs=('x', 'y'))

    net = ADCpt(EpicsSignalRO, 'Net_RBV')
    profile_average = DDC(ad_group(EpicsSignalRO,
                                   (('x', 'ProfileAverageX_RBV'),
                                    ('y', 'ProfileAverageY_RBV'))),
                          doc='Profile average in XY',
                          default_read_attrs=('x', 'y'))

    profile_centroid = DDC(ad_group(EpicsSignalRO,
                                    (('x', 'ProfileCentroidX_RBV'),
                                     ('y', 'ProfileCentroidY_RBV'))),
                           doc='Profile centroid in XY',
                           default_read_attrs=('x', 'y'))

    profile_cursor = DDC(ad_group(EpicsSignalRO,
                                  (('x', 'ProfileCursorX_RBV'),
                                   ('y', 'ProfileCursorY_RBV'))),
                         doc='Profile cursor in XY',
                         default_read_attrs=('x', 'y'))

    profile_size = DDC(ad_group(EpicsSignalRO, (('x', 'ProfileSizeX_RBV'),
                                                ('y', 'ProfileSizeY_RBV'))),
                       doc='Profile size in XY',
                       default_read_attrs=('x', 'y'))

    profile_threshold = DDC(ad_group(EpicsSignalRO,
                                     (('x', 'ProfileThresholdX_RBV'),
                                      ('y', 'ProfileThresholdY_RBV'))),
                            doc='Profile threshold in XY',
                            default_read_attrs=('x', 'y'))

    set_xhopr = ADCpt(EpicsSignal, 'SetXHOPR')
    set_yhopr = ADCpt(EpicsSignal, 'SetYHOPR')
    sigma_xy = ADCpt(EpicsSignalRO, 'SigmaXY_RBV')
    sigma_x = ADCpt(EpicsSignalRO, 'SigmaX_RBV')
    sigma_y = ADCpt(EpicsSignalRO, 'SigmaY_RBV')
    sigma = ADCpt(EpicsSignalRO, 'Sigma_RBV')
    # ts_acquiring = ADCpt(EpicsSignal, 'TS:TSAcquiring')

    ts_centroid = DDC(ad_group(EpicsSignal, (('x', 'TS:TSCentroidX'),
                                             ('y', 'TS:TSCentroidY'))),
                      doc='Time series centroid in XY',
                      default_read_attrs=('x', 'y'))

    # ts_control = ADCpt(EpicsSignal, 'TS:TSControl', string=True)
    # ts_current_point = ADCpt(EpicsSignal, 'TS:TSCurrentPoint')
    ts_max_value = ADCpt(EpicsSignal, 'TS:TSMaxValue')

    ts_max = DDC(ad_group(EpicsSignal,
                          (('x', 'TS:TSMaxX'), ('y', 'TS:TSMaxY'))),
                 doc='Time series maximum in XY',
                 default_read_attrs=('x', 'y'))

    ts_mean_value = ADCpt(EpicsSignal, 'TS:TSMeanValue')
    ts_min_value = ADCpt(EpicsSignal, 'TS:TSMinValue')

    ts_min = DDC(ad_group(EpicsSignal,
                          (('x', 'TS:TSMinX'), ('y', 'TS:TSMinY'))),
                 doc='Time series minimum in XY',
                 default_read_attrs=('x', 'y'))

    ts_net = ADCpt(EpicsSignal, 'TS:TSNet')
    # ts_num_points = ADCpt(EpicsSignal, 'TS:TSNumPoints')
    ts_read = ADCpt(EpicsSignal, 'TS:TSRead')
    ts_sigma = ADCpt(EpicsSignal, 'TS:TSSigma')
    ts_sigma_x = ADCpt(EpicsSignal, 'TS:TSSigmaX')
    ts_sigma_xy = ADCpt(EpicsSignal, 'TS:TSSigmaXY')
    ts_sigma_y = ADCpt(EpicsSignal, 'TS:TSSigmaY')
    ts_total = ADCpt(EpicsSignal, 'TS:TSTotal')
    total = ADCpt(EpicsSignalRO, 'Total_RBV')
예제 #15
0
class Bimorph(Device):
    '''Bimorph HV Power Source'''

    bank_no = C(EpicsSignal, ':BANK_NO_32.VAL')
    step_size = C(EpicsSignal, ':U_STEP.VAL')
    inc_bank = C(EpicsSignal, ':INCR_U_BANK_CMD.PROC')
    dec_bank = C(EpicsSignal, ':DECR_U_BANK_CMD.PROC')
    stop_ramp = C(EpicsSignal, ':STOP_RAMPS_BANK.PROC')
    start_ramp = C(EpicsSignal, ':START_RAMPS_CMD.PROC')

    format_number = C(EpicsSignal, ':FORMAT_NO_SP.VAL')
    load_format = C(EpicsSignal, ':FORMAT_ACTIVE_SP.PROC')

    all_target_voltages = C(EpicsSignalRO, ':U_ALL_TARGET_MON.VAL')
    all_current_voltages = C(EpicsSignalRO, ':U_ALL_CURRENT_MON.VAL')

    unit_status = C(EpicsSignalRO, ':UNIT_STATUS_MON.A')

    channels = DDC(add_channels(range(0, 32)))

    def step(self, bank, size, direction, start=False, wait=False):
        self.bank_no.put(bank)
        self.step_size.put(size)

        if (direction == "inc"):
            self.inc_bank.put(1)
        else:
            self.dec_bank.put(1)

        if (start):
            self.start()

        if (wait):
            self.wait()

    def increment_bank(self, bank, size, start=False, wait=False):
        ''' Increments the target voltage in `size` Volts in the specified `bank`

        Parameters:
        -----------
        bank : int
            The number of the bank to be incremented
        size : float
            The amount of Volts to increment from the bank target value
        start : bool
            Determines if the ramp must start right after the increment. Defaults to False.
        wait : bool
            Determines if the code must wait until the ramp process finishes. Defaults to False.
        '''
        self.step(bank, size, "inc", start)

    def decrement_bank(self, bank, size, start=False, wait=False):
        ''' Decrements the target voltage in `size` Volts in the specified `bank`

        Parameters:
        -----------
        bank : int
            The number of the bank to be decremented
        size : float
            The amount of Volts to decrement from the bank target value
        start : bool
            Determines if the ramp must start right after the decrement. Defaults to False.
        wait : bool
            Determines if the code must wait until the ramp process finishes. Defaults to False.
        '''
        self.step(bank, size, "dec", start)

    def start(self):
        ''' Start the Ramping process on all channels '''
        self.start_ramp.put(1)

    def stop(self):
        ''' Stops the Ramping process on all channels '''
        self.stop_ramp.put(1)

    def is_ramping(self):
        ''' Returns wether the power supply is ramping or not '''
        return (int(self.unit_status.get()) >> 30) == 1

    def is_interlock_ok(self):
        ''' Returns the interlock state '''
        st = int(self.unit_status.get())
        return (st & 1) & ((st >> 1) & 1) == 1

    def is_on(self):
        ''' Returns wether the Channels are ON or OFF '''
        return (int(self.unit_status.get()) >> 29) == 1

    def wait(self):
        while self.is_ramping():
            sleep(0.1)
예제 #16
0
class ScalerCH(Device):
    _default_configuration_attrs = ('preset_time', 'freq', 'auto_count_time',
                                    'count_mode', 'delay', 'auto_count_delay',
                                    'egu', 'channels')

    _default_read_attrs = ('time', 'channels')

    # The data
    channels = DDC(_sc_chans('chan', range(1, 33)))

    # tigger + trigger mode
    count = C(EpicsSignal, '.CNT', trigger_value=1)
    count_mode = C(EpicsSignal, '.CONT', string=True)

    # delay from triggering to starting counting
    delay = C(EpicsSignal, '.DLY')
    auto_count_delay = C(EpicsSignal, '.DLY1')

    time = C(EpicsSignal, '.T')
    freq = C(EpicsSignal, '.FREQ')

    preset_time = C(EpicsSignal, '.TP')
    auto_count_time = C(EpicsSignal, '.TP1')

    update_rate = C(EpicsSignal, '.RATE')
    auto_count_update_rate = C(EpicsSignal, '.RAT1')

    egu = C(EpicsSignal, '.EGU')

    def __init__(self, *args, **kwargs):

        super().__init__(*args, **kwargs)

        self.channels.read_attrs = ['chan01']
        self.channels.configuration_attrs = ['chan01']

    def match_names(self):
        for s in self.channels.component_names:
            getattr(self.channels, s).match_name()

    def select_channels(self, chan_names):
        '''Select channels based on the EPICS name PV

        Parameters
        ----------
        chan_names : Iterable[str]

            The names (as reported by the channel.chname signal)
            of the channels to select.
        '''
        self.match_names()
        name_map = {
            getattr(self.channels, s).name.get(): s
            for s in self.channels.component_names
        }

        read_attrs = ['chan01']  # always include time
        for ch in chan_names:
            try:
                read_attrs.append(name_map[ch])
            except KeyError:
                raise RuntimeError("The channel {} is not configured "
                                   "on the scaler.  The named channels are "
                                   "{}".format(ch, tuple(name_map)))
        self.channels.read_attrs = list(read_attrs)
        self.channels.configuration_attrs = list(read_attrs)
        self.hints = {
            'fields':
            [getattr(self.channels, ch).s.name for ch in read_attrs[1:]]
        }
예제 #17
0
파일: sscan.py 프로젝트: tangkong/apstools
class SscanRecord(Device):
    """
    EPICS synApps sscan record: used as $(P):scan(N)

    .. autosummary::
       
        ~defined_in_EPICS
        ~reset
        ~select_channels

    """

    desc = Cpt(EpicsSignal, '.DESC', kind=Kind.config)
    scan_phase = Cpt(EpicsSignalRO, '.FAZE')
    data_state = Cpt(EpicsSignalRO, '.DSTATE')
    data_ready = Cpt(EpicsSignalRO, '.DATA')
    scan_busy = Cpt(EpicsSignalRO, '.BUSY')
    alert_flag = Cpt(EpicsSignalRO, '.ALRT')
    alert_message = Cpt(EpicsSignalRO, '.SMSG')
    number_points = Cpt(EpicsSignal, '.NPTS', kind=Kind.config)
    maximum_number_points = Cpt(EpicsSignal, '.MPTS', kind=Kind.config)
    current_point = Cpt(EpicsSignalRO, '.CPT')
    pasm = Cpt(EpicsSignal, '.PASM')
    execute_scan = Cpt(EpicsSignal, '.EXSC')
    bspv = Cpt(EpicsSignal, '.BSPV', kind=Kind.config)
    bscd = Cpt(EpicsSignal, '.BSCD')
    bswait = Cpt(EpicsSignal, '.BSWAIT')
    cmnd = Cpt(EpicsSignal, '.CMND')
    detector_delay = Cpt(EpicsSignal, '.DDLY')
    positioner_delay = Cpt(EpicsSignal, '.PDLY')
    reference_detector = Cpt(EpicsSignal, '.REFD', kind=Kind.config)
    wait = Cpt(EpicsSignal, '.WAIT')
    wcnt = Cpt(EpicsSignalRO, '.WCNT')
    awct = Cpt(EpicsSignal, '.AWCT')
    acqt = Cpt(EpicsSignal, '.ACQT')
    acqm = Cpt(EpicsSignal, '.ACQM')
    atime = Cpt(EpicsSignal, '.ATIME')
    copyto = Cpt(EpicsSignal, '.COPYTO')
    a1pv = Cpt(EpicsSignal, '.A1PV', kind=Kind.config)
    a1nv = Cpt(EpicsSignal, '.A1NV', kind=Kind.config)
    a1cd = Cpt(EpicsSignal, '.A1CD')
    aspv = Cpt(EpicsSignal, '.ASPV', kind=Kind.config)
    ascd = Cpt(EpicsSignal, '.ASCD')

    positioners = DDC(_sscan_positioners("1 2 3 4".split()))
    detectors = DDC(_sscan_detectors(APS_utils.itemizer("%02d", range(1, 71))))
    triggers = DDC(_sscan_triggers("1 2 3 4".split()))

    def set(self, value, **kwargs):
        """interface to use bps.mv()"""
        if value != 1:
            return

        working_status = DeviceStatus(self)
        started = False

        def execute_scan_cb(value, timestamp, **kwargs):
            value = int(value)
            if started and value == 0:
                working_status._finished()

        self.execute_scan.subscribe(execute_scan_cb)
        self.execute_scan.set(1)
        started = True
        return working_status

    def reset(self):
        """set all fields to default values"""
        self.desc.put(self.desc.pvname.split(".")[0])
        self.number_points.put(1000)
        for part in (self.positioners, self.detectors, self.triggers):
            for ch_name in part.component_names:
                channel = getattr(part, ch_name)
                channel.reset()
        self.a1pv.put("")
        self.acqm.put("NORMAL")
        if self.name.find("scanH") > 0:
            self.acqt.put("1D ARRAY")
        else:
            self.acqt.put("SCALAR")
        self.aspv.put("")
        self.bspv.put("")
        self.pasm.put("STAY")
        self.bswait.put("Wait")
        self.a1cd.put(1)
        self.ascd.put(1)
        self.bscd.put(1)
        self.reference_detector.put(1)
        self.atime.put(0)
        self.awct.put(0)
        self.copyto.put(0)
        self.detector_delay.put(0)
        self.positioner_delay.put(0)
        while self.wcnt.get() > 0:
            self.wait.put(0)

    def select_channels(self):
        """
        Select channels that are configured in EPICS
        """
        for part in (self.positioners, self.detectors, self.triggers):
            channel_names = []  # part.get_configured_channels()
            channel_names = [
                ch for ch in part.component_names
                if getattr(part, ch).defined_in_EPICS
            ]

            part.configuration_attrs = channel_names
            part.read_attrs = channel_names
            part.kind = Kind.normal

    @property
    def defined_in_EPICS(self):
        """True if will be used in EPICS"""
        self.select_channels()
        channels = len(self.positioners.read_attrs)
        channels += len(self.detectors.read_attrs)
        #channels += len(self.triggers.read_attrs)
        return channels > 0
예제 #18
0
파일: calcout.py 프로젝트: aps-7bm/apstools
class CalcoutRecord(EpicsRecordFloatFields, EpicsRecordDeviceCommonAll):
    """
    EPICS calcout record support in ophyd

	.. autosummary::

		~reset

    :see: https://wiki-ext.aps.anl.gov/epics/index.php/RRM_3-14_Calcout
    """
    units = Cpt(EpicsSignal, ".EGU")
    precision = Cpt(EpicsSignal, ".PREC")

    calculated_value = Cpt(EpicsSignal, ".VAL")
    calculation = Cpt(EpicsSignal, ".CALC")

    output_pv = Cpt(EpicsSignal, ".OUT")
    output_execute_option = Cpt(EpicsSignal, ".OOPT")
    output_execution_delay = Cpt(EpicsSignal, ".ODLY")
    output_data_option = Cpt(EpicsSignal, ".DOPT")
    output_calculation = Cpt(EpicsSignal, ".OCAL")
    output_value = Cpt(EpicsSignal, ".OVAL")
    invalid_output_action = Cpt(EpicsSignal, ".IVOA")
    invalid_output_value = Cpt(EpicsSignal, ".IVOV")
    event_to_issue = Cpt(EpicsSignal, ".OEVT")

    output_pv_status = Cpt(EpicsSignal, ".OUTV")
    calculation_valid = Cpt(EpicsSignal, ".CLCV")
    output_calculation_valid = Cpt(EpicsSignal, ".OCLV")
    output_delay_active = Cpt(EpicsSignal, ".DLYA")

    channels = DDC(_channels(CHANNEL_LETTERS_LIST))

    read_attrs = APS_utils.itemizer("channels.%s", CHANNEL_LETTERS_LIST)
    hints = {'fields': read_attrs}

    @property
    def value(self):
        return self.calculated_value.value

    def reset(self):
        """set all fields to default values"""
        pvname = self.description.pvname.split(".")[0]
        self.scanning_rate.put("Passive")
        self.description.put(pvname)
        self.units.put("")
        self.precision.put("5")

        self.calculation.put("")
        self.calculated_value.put(0)
        self.output_calculation.put("")
        self.output_value.put(0)

        self.forward_link.put("")
        self.output_pv.put("")
        self.invalid_output_action.put(0)
        self.invalid_output_value.put(0)

        self.output_execution_delay.put(0)
        self.output_execute_option.put(0)
        self.output_data_option.put(0)

        for letter in self.channels.read_attrs:
            channel = getattr(self.channels, letter)
            if isinstance(channel, CalcoutRecordChannel):
                channel.reset()
        self.hints = {
            'fields': ["channels.%s" % c for c in CHANNEL_LETTERS_LIST]
        }
        self.read_attrs = ["channels.%s" % c for c in CHANNEL_LETTERS_LIST]
예제 #19
0
class SscanRecord(RecordBase):
    detectors = DDC(_make_detectors(1, 71))
    positioners = DDC(_make_positioners(1, 5))
    readbacks = DDC(_make_readbacks(1, 5))
    triggers = DDC(_make_triggers(1, 5))

    a1_pv_status = Cpt(EpicsSignalRO, '.A1NV')
    abort_right_now = Cpt(EpicsSignalRO, '.KILL')
    after_scan_pv_status = Cpt(EpicsSignalRO, '.ASNV')
    alarm_status = Cpt(EpicsSignalRO, '.STAT')
    auto_wait_count = Cpt(EpicsSignal, '.AWCT')
    beforescan_pv_status = Cpt(EpicsSignalRO, '.BSNV')
    buffered_current_point = Cpt(EpicsSignalRO, '.BCPT')
    code_version = Cpt(EpicsSignalRO, '.VERS')
    command_field = Cpt(EpicsSignal, '.CMND')
    current_point = Cpt(EpicsSignalRO, '.CPT')
    desired_point = Cpt(EpicsSignal, '.DPT')
    execute_scan = Cpt(EpicsSignal, '.EXSC')
    go_pause_control = Cpt(EpicsSignal, '.PAUS')
    internal_execscan = Cpt(EpicsSignalRO, '.XSC')

    last_value_of_go_pause = Cpt(EpicsSignalRO, '.LPAU')
    operator_alert = Cpt(EpicsSignalRO, '.ALRT')
    point_oflast_posting = Cpt(EpicsSignalRO, '.PCPT')
    previous_xscan = Cpt(EpicsSignalRO, '.PXSC')
    record_state_msg = Cpt(EpicsSignal, '.SMSG$', string=True)
    reference_detector = Cpt(EpicsSignal, '.REFD')
    scan_data_ready = Cpt(EpicsSignalRO, '.DATA')
    scan_in_progress = Cpt(EpicsSignalRO, '.BUSY')
    scan_phase = Cpt(EpicsSignalRO, '.FAZE')
    wait_count = Cpt(EpicsSignalRO, '.WCNT')
    wait_for_client_s = Cpt(EpicsSignal, '.WAIT')
    waiting_for_client_s = Cpt(EpicsSignalRO, '.WTNG')
    waiting_for_data_storage_client = Cpt(EpicsSignal, '.AWAIT')

    # - calc
    after_scan_pv_name = Cpt(EpicsSignal, '.ASPV$', string=True)
    array_read_trigger_1_pv_name = Cpt(EpicsSignal, '.A1PV$', string=True)
    before_scan_pv_name = Cpt(EpicsSignal, '.BSPV$', string=True)

    # - common
    acquisition_mode = Cpt(EpicsSignal, '.ACQM')
    acquisition_type = Cpt(EpicsSignal, '.ACQT')
    copy_last_pt_thru = Cpt(EpicsSignal, '.COPYTO')
    data_state = Cpt(EpicsSignalRO, '.DSTATE')

    # - inputs
    a1_command = Cpt(EpicsSignal, '.A1CD')
    after_scan_command = Cpt(EpicsSignal, '.ASCD')
    array_post_time_period = Cpt(EpicsSignal, '.ATIME')
    autowait_for_data_storage_client = Cpt(EpicsSignal, '.AAWAIT')
    before_scan_command = Cpt(EpicsSignal, '.BSCD')
    detector_settling_delay = Cpt(EpicsSignal, '.DDLY')
    pause_resume_delay = Cpt(EpicsSignal, '.RDLY')
    positioner_settling_delay = Cpt(EpicsSignal, '.PDLY')
    wait_for_completion = Cpt(EpicsSignal, '.ASWAIT')
    wait_for_completion_bswait = Cpt(EpicsSignal, '.BSWAIT')

    # - links
    max_of_points = Cpt(EpicsSignalRO, '.MPTS')
    number_of_points = Cpt(EpicsSignal, '.NPTS')

    # - output
    after_scan_mode = Cpt(EpicsSignal, '.PASM')
    freeze_flag_override = Cpt(EpicsSignal, '.FFO')
    freeze_num_of_points = Cpt(EpicsSignal, '.FPTS')
예제 #20
0
class EpicsSscanRecord(Device):
    """EPICS synApps sscan record: used as $(P):userCalc$(N)"""

    desc = Cpt(EpicsSignal, '.DESC')
    faze = Cpt(EpicsSignalRO, '.FAZE')
    data_state = Cpt(EpicsSignalRO, '.DSTATE')
    npts = Cpt(EpicsSignal, '.NPTS')
    cpt = Cpt(EpicsSignalRO, '.CPT')
    pasm = Cpt(EpicsSignal, '.PASM')
    exsc = Cpt(EpicsSignal, '.EXSC')
    bspv = Cpt(EpicsSignal, '.BSPV')
    bscd = Cpt(EpicsSignal, '.BSCD')
    bswait = Cpt(EpicsSignal, '.BSWAIT')
    cmnd = Cpt(EpicsSignal, '.CMND')
    ddly = Cpt(EpicsSignal, '.DDLY')
    pdly = Cpt(EpicsSignal, '.PDLY')
    refd = Cpt(EpicsSignal, '.REFD')
    wait = Cpt(EpicsSignal, '.WAIT')
    wcnt = Cpt(EpicsSignalRO, '.WCNT')
    awct = Cpt(EpicsSignal, '.AWCT')
    acqt = Cpt(EpicsSignal, '.ACQT')
    acqm = Cpt(EpicsSignal, '.ACQM')
    atime = Cpt(EpicsSignal, '.ATIME')
    copyto = Cpt(EpicsSignal, '.COPYTO')
    a1pv = Cpt(EpicsSignal, '.A1PV')
    a1cd = Cpt(EpicsSignal, '.A1CD')
    aspv = Cpt(EpicsSignal, '.ASPV')
    ascd = Cpt(EpicsSignal, '.ASCD')

    positioners = DDC(_sscan_positioners("1 2 3 4".split()))
    detectors = DDC(_sscan_detectors(["%02d" % k for k in range(1, 71)]))
    triggers = DDC(_sscan_triggers("1 2 3 4".split()))

    def reset(self):
        """set all fields to default values"""
        self.desc.put(self.desc.pvname.split(".")[0])
        self.npts.put(1000)
        for part in (self.positioners, self.detectors, self.triggers):
            for ch_name in part.read_attrs:
                channel = part.__getattr__(ch_name)
                channel.reset()
        self.a1pv.put("")
        self.acqm.put("NORMAL")
        if self.name.find("scanH") > 0:
            self.acqt.put("1D ARRAY")
        else:
            self.acqt.put("SCALAR")
        self.aspv.put("")
        self.bspv.put("")
        self.pasm.put("STAY")
        self.bswait.put("Wait")
        self.a1cd.put(1)
        self.ascd.put(1)
        self.bscd.put(1)
        self.refd.put(1)
        self.atime.put(0)
        self.awct.put(0)
        self.copyto.put(0)
        self.ddly.put(0)
        self.pdly.put(0)
        while self.wcnt.get() > 0:
            self.wait.put(0)