def fly_body(): yield from bps.trigger_and_read([E_centers], name='energy_bins') for y in range(num_scans): # go to start of row yield from bps.mv(mono.linear, l_start) # set the fly speed yield from bps.mv(mono.linear.velocity, flyspeed) yield from bps.trigger_and_read([mono], name='row_ends') for v in ['p1600=0', 'p1600=1']: yield from bps.mv(dtt, v) yield from bps.sleep(0.1) # arm the struck yield from bps.trigger(sclr, group=f'fly_energy_{y}') # fly the motor yield from bps.abs_set(mono.linear, l_stop + a_l_step_size, group=f'fly_energy_{y}') yield from bps.wait(group=f'fly_energy_{y}') yield from bps.trigger_and_read([mono], name='row_ends') yield from bps.mv(mono.linear.velocity, 0.5) # hard coded to let the sclr count its fingers and toes yield from bps.sleep(.1) # read and save the struck yield from bps.create(name='primary') yield from bps.read(sclr) yield from bps.save()
def _plan(self): yield from bps.open_run() # stash numcapture and shutter_enabled num_capture = yield from bps.rd(self.device.hdf5.num_capture) shutter_enabled = yield from bps.rd(self.device.dg1.shutter_enabled) # set to 1 temporarily self.device.hdf5.num_capture.put(1) # Restage to ensure that dark frames goes into a separate file. yield from bps.stage(self.device) yield from bps.mv(self.device.dg1.shutter_enabled, 2) # The `group` parameter passed to trigger MUST start with # bluesky-darkframes-trigger. yield from bps.trigger_and_read([self.device], name='dark') # Restage. yield from bps.unstage(self.device) # restore numcapture and shutter_enabled yield from bps.mv(self.device.hdf5.num_capture, num_capture) yield from bps.mv(self.device.dg1.shutter_enabled, shutter_enabled) # Dark frames finished, moving on to data yield from bps.stage(self.device) status = yield from bps.trigger(self.device, group='primary-trigger') while not status.done: yield from bps.trigger_and_read(self.async_poll_devices, name='labview') yield from bps.sleep(1) yield from bps.create('primary') yield from bps.read(self.device) yield from bps.save() yield from bps.unstage(self.device)
def test_trigger_and_read(hw): det = hw.det msgs = list(trigger_and_read([det])) expected = [ Msg('trigger', det), Msg('wait'), Msg('create', name='primary'), Msg('read', det), Msg('save') ] for msg in msgs: msg.kwargs.pop('group', None) assert msgs == expected msgs = list(trigger_and_read([det], 'custom')) expected = [ Msg('trigger', det), Msg('wait'), Msg('create', name='custom'), Msg('read', det), Msg('save') ] for msg in msgs: msg.kwargs.pop('group', None) assert msgs == expected
def myplan(dets): ''' Simple plan to trigger two detectors. Meant for test only. ''' for msg in trigger_and_read([dets[0]], name='primary'): yield msg for msg in trigger_and_read([dets[1]], name='secondary'): yield msg
def one_1d_step(detectors, motor, step): """ Inner loop of a 1D step scan This is the default function for ``per_step`` param in 1D plans. """ yield from checkpoint() yield from abs_set(motor, step, wait=True) yield from trigger_and_read(list(detectors) + [motor], name="dark") return (yield from trigger_and_read(list(detectors) + [motor]))
def sim_plan_outer(npts): for j in range(int(npts / 2)): yield from bps.mov(hw.motor, j * 0.2) yield from bps.trigger_and_read([hw.motor, hw.det]) yield from sim_plan_inner(npts + 1) for j in range(int(npts / 2), npts): yield from bps.mov(hw.motor, j * 0.2) yield from bps.trigger_and_read([hw.motor, hw.det])
def wait_for_value(det, field, position, atol, delay=0.5): # Initial reading reading = yield from trigger_and_read(det) curr = reading[field]['value'] # Repeat until the operator responds while not np.isclose(curr, position, atol=atol): reading = yield from trigger_and_read(det) curr = reading[field]['value'] if delay: yield from sleep(delay)
def plan(): # working around 'yield from' here which breaks py2 for msg in configure(det, {'z': 3}): # no-op yield msg for msg in trigger_and_read([det]): yield msg # changing the config after a read generates a new Event Descriptor for msg in configure(det, {'z': 4}): yield msg for msg in trigger_and_read([det]): yield msg
def sim_multirun_plan_nested(npts: int, delay: float = 1.0): for j in range(int(npts / 2)): yield from bps.mov(motor, j * 0.2) yield from bps.trigger_and_read([motor, det]) yield from bps.sleep(delay) yield from _sim_plan_inner(npts + 1, delay) for j in range(int(npts / 2), npts): yield from bps.mov(motor, j * 0.2) yield from bps.trigger_and_read([motor, det]) yield from bps.sleep(delay)
def plan(npts): for j in range(int(npts/2)): yield from bps.mov(hw.motor1, j * 0.2) yield from bps.trigger_and_read([hw.motor1, hw.det1]) # Different parameter values may be passed to the recursively called plans yield from sim_plan_recursive(npts + 2) for j in range(int(npts/2), npts): yield from bps.mov(hw.motor1, j * 0.2) yield from bps.trigger_and_read([hw.motor1, hw.det1])
def light_dark_nd_step(detectors, step, pos_cache): """ Inner loop of an N-dimensional step scan This is the default function for ``per_step`` param`` in ND plans. Parameters ---------- detectors : iterable devices to read step : dict mapping motors to positions in this step pos_cache : dict mapping motors to their last-set positions """ def move(): yield Msg("checkpoint") grp = _short_uid("set") for motor, pos in step.items(): if pos == pos_cache[motor]: # This step does not move this motor. continue yield Msg("set", motor, pos, group=grp) pos_cache[motor] = pos yield Msg("wait", None, group=grp) motors = step.keys() yield from close_shutter_stub() yield from move() for k, v in sub_sample_dict.items(): if np.abs(sample_motor.get().user_readback - k) < 1.5: inner_dict = v break else: inner_dict = {"exposure": .1, "wait": 1} print(inner_dict) yield from configure_area_det_expo(inner_dict["exposure"]) # This is to make certain that the detector has properly configured the # exposure time, uncomment if waits don't work # yield from bps.sleep(10) yield from bps.trigger_and_read(list(detectors) + list(motors) + [shutter], name="dark") yield from open_shutter_stub() t0 = time.time() yield from bps.trigger_and_read(list(detectors) + list(motors) + [shutter]) t1 = time.time() print("INFO: exposure time (plus minor message overhead) = {:.2f}".format( t1 - t0)) yield from close_shutter_stub() yield from bps.sleep(inner_dict["wait"])
def filter_opt_count(det, target_count=100000, md={}): """ filter_opt_count OPtimize counts using filters Assumes mu=0.2, x = [0.89, 2.52, 3.83, 10.87] I = I_o \exp(-mu*x) Only takes one detector, since we are optimizing based on it alone target is mean+2std """ dc = DocumentCache() token = yield from bps.subscribe('all', dc) yield from bps.stage(det) md = {} yield from bps.open_run(md=md) # BlueskyRun object allows interaction with documents similar to db.v2, # but documents are in memory run = BlueskyRun(dc) yield from bps.trigger_and_read([det, filter1, filter2, filter3, filter4]) data = run.primary.read()['pilatus300k_image'] mean = data[-1].mean().values.item() # xarray.DataArray methods std = data[-1].std().values.item() # xarray.DataArray methods curr_counts = mean + 2 * std # gather filter information and solve filter_status = [ round(filter1.get() / 5), round(filter2.get() / 5), round(filter3.get() / 5), round(filter4.get() / 5) ] print(filter_status) filter_status = [not e for e in filter_status] new_filters = solve_filter_setup(filter_status, curr_counts, target_count) # invert again to reflect filter status new_filters = [not e for e in new_filters] print(new_filters) # set new filters and read. For some reason hangs on bps.mv when going high filter1.put(new_filters[0] * 4.9) filter2.put(new_filters[1] * 4.9) filter3.put(new_filters[2] * 4.9) filter4.put(new_filters[3] * 4.9) yield from bps.trigger_and_read([det, filter1, filter2, filter3, filter4]) # close out run yield from bps.close_run() yield from bps.unsubscribe(token) yield from bps.unstage(det)
def fly_row(): # go to start of row target_y = ystart + y * a_ystep_size yield from bps.mv(xy_fly_stage.x, xstart, xy_fly_stage.y, target_y) yield from bps.mv(y_centers, np.ones(num_xpixels) * target_y) # set the fly speed ret = yield from bps.read(xy_fly_stage.z.user_readback) # (in mm) zpos = (ret[xy_fly_stage.z.user_readback.name]["value"] if ret is not None else 0) yield from bps.mov(z_centers, np.ones(num_xpixels) * zpos) yield from bps.mv(xy_fly_stage.x.velocity, flyspeed) yield from bps.trigger_and_read([xy_fly_stage], name="row_ends") for v in ["p1600=0", "p1600=1"]: yield from bps.mv(dtt, v) yield from bps.sleep(0.1) # arm the struck yield from bps.trigger(sclr, group=f"fly_row_{y}") # maybe start the xspress3 if xspress3 is not None: yield from bps.trigger(xspress3, group=f"fly_row_{y}") yield from bps.sleep(0.1) # fly the motor yield from bps.abs_set(xy_fly_stage.x, xstop + a_xstep_size, group=f"fly_row_{y}") yield from bps.wait(group=f"fly_row_{y}") yield from bps.trigger_and_read([xy_fly_stage], name="row_ends") yield from bps.mv(xy_fly_stage.x.velocity, 5.0) yield from bps.sleep(0.1) # read and save the struck yield from bps.create(name="primary") # yield from bps.read(sclr) yield from bps.read(mono) yield from bps.read(x_centers) yield from bps.read(y_centers) yield from bps.read(z_centers) yield from bps.read(xy_fly_stage.y) yield from bps.read(xy_fly_stage.z) # and maybe the xspress3 if xspress3 is not None: yield from bps.read(xspress3) yield from bps.save()
def test_trigger_and_read(hw): det = hw.det msgs = list(trigger_and_read([det])) expected = [Msg('trigger', det), Msg('wait'), Msg('create', name='primary'), Msg('read', det), Msg('save')] for msg in msgs: msg.kwargs.pop('group', None) assert msgs == expected msgs = list(trigger_and_read([det], 'custom')) expected = [Msg('trigger', det), Msg('wait'), Msg('create', name='custom'), Msg('read', det), Msg('save')] for msg in msgs: msg.kwargs.pop('group', None) assert msgs == expected
def test_read_clash(RE): dcm = DCM('', name='dcm') dcm2 = DCM('', name='dcm') with pytest.raises(ValueError): RE(([Msg('open_run')] + list(trigger_and_read([dcm, dcm2.th])) + [Msg('close_run')])) with pytest.raises(ValueError): RE(([Msg('open_run')] + list(trigger_and_read([dcm, dcm2])) + [Msg('close_run')])) with pytest.raises(ValueError): RE(([Msg('open_run')] + list(trigger_and_read([dcm.th, dcm2.th])) + [Msg('close_run')]))
def one_nd_step(detectors, step, pos_cache): """ Inner loop of an N-dimensional step scan This is the default function for ``per_step`` param`` in ND plans. Parameters ---------- detectors : iterable devices to read step : dict mapping motors to positions in this step pos_cache : dict mapping motors to their last-set positions """ def move(): yield Msg('checkpoint') for motor, pos in step.items(): if pos == pos_cache[motor]: # This step does not move this motor. continue yield from bps.mov(motor, pos) pos_cache[motor] = pos motors = step.keys() yield from move() yield from bps.trigger_and_read(list(detectors) + list(motors))
def motor_dark_step(detectors, motor, step): """ Take darks while moving motors, wait for all to be finished before taking light """ yield from bps.checkpoint() print('l120') # close the shutter #yield from _close_shutter_stub() COMMENTED OUT (dark per light) print('l123') # move motors don't wait yet. # Note for Soham: use `group=None` to ramp temp after dark collected # (Broken and replaced below) yield from bps.abs_set(motor, step, group="dark_motor") yield from bps.abs_set(motor, step, group="dark_motor") print('l127') # take dark (this has an internal wait on the readback) #yield from bps.trigger_and_read(list(detectors), name="dark") COMMENTED OUT (dark per light) print('l130') # (Broken) now wait for the motors to be done too yield from bps.wait(group="dark_motor") print('l133') # open shutter yield from open_shutter_stub() print('l136') # take data yield from bps.trigger_and_read(list(detectors) + [motor]) print('l139')
def per_step_plan(detectors, motors, actions, *args, log=None, **kwargs): '''execute one step and return detecors readings Applies the actions to the motors and reads the detectors. Args: detectors: detectors to read from motors: motors to apply the actions to actions: keras-rl requested actions Returns: the detector readings. ''' if log is None: log = logger motors = list(motors) action = list(actions) # There should be a func ml = [] for m, a in zip(motors, action): ml.extend([m, a]) args = tuple(ml) log.debug(f'Executing move (bps.mv) {args}') yield from bps.mv(*args) r = (yield from bps.trigger_and_read(detectors)) log.debug(f'Read {detectors} to {r}') return r
def optimize_energy_per_step(detectors, step, pos_cache): """ Our custom function for ``per_step`` param`` in grid_scan below. Parameters ---------- detectors : iterable devices to read step : dict mapping motors to positions in this step pos_cache : dict mapping motors to their last-set positions """ def move(): yield Msg('checkpoint') grp = _short_uid('set') for motor, pos in step.items(): if pos == pos_cache[motor]: # This step does not move this motor. continue yield Msg('set', motor, pos, group=grp) pos_cache[motor] = pos yield Msg('wait', None, group=grp) motors = step.keys() yield from move() yield from optimize_energy_with_sscan_record() yield from bps.trigger_and_read(list(detectors) + list(motors))
def plan(reader): yield from bps.null() for i in range(10): assert daq.state == 'Running' yield from bps.trigger_and_read([reader]) assert daq.state == 'Running' yield from bps.null()
def collect_white_field(experiment, cfg_tomo, atfront=True): """ Collect white/flat field images by moving the sample out of the FOV """ # unpack devices det = experiment.det tomostage = experiment.tomostage # move sample out of the way _x = cfg_tomo['fronte_white_ksamX'] if atfront else cfg_tomo[ 'back_white_ksamX'] _z = cfg_tomo['fronte_white_ksamZ'] if atfront else cfg_tomo[ 'back_white_ksamZ'] yield from bps.mv(tomostage.ksamX, _x) yield from bps.mv(tomostage.ksamZ, _z) # setup detector yield from bps.mv(det.hdf1.nd_array_port, 'PROC1') yield from bps.mv(det.tiff1.nd_array_port, 'PROC1') yield from bps.mv(det.proc1.enable, 1) yield from bps.mv(det.proc1.reset_filter, 1) yield from bps.mv(det.proc1.num_filter, cfg_tomo['n_frames']) yield from bps.mv(det.cam.trigger_mode, "Internal") yield from bps.mv(det.cam.image_mode, "Multiple") yield from bps.mv(det.cam.num_images, cfg_tomo['n_frames'] * cfg_tomo['n_white']) yield from bps.trigger_and_read([det]) # move sample back to FOV # NOTE: # not sure is this will work or not... yield from bps.mv(tomostage.samX, cfg_tomo['initial_ksamX']) yield from bps.mv(tomostage.samY, cfg_tomo['initial_ksamZ'])
def insert_dark_frame(force_read, msg=None): # Acquire a fresh Snapshot if we need one, or retrieve a cached one. state = {} for signal in self.locked_signals: reading = yield from bluesky.plan_stubs.read(signal) # Restructure # {'data_key': {'value': <value>, 'timestamp': <timestamp>}, ...} # into (('data_key', <value>) ...). values_only = tuple( (k, v['value']) for k, v in reading.items()) state[signal.name] = values_only if self._current_state != state: self._current_state = state snapshot_changed = True else: snapshot_changed = False try: snapshot = self.get_snapshot(state) except NoMatchingSnapshot: logger.info(f"Taking a new dark frame for state=%r", state) snapshot = yield from self.dark_plan() self.add_snapshot(snapshot, state) if snapshot_changed or force_read: logger.info(f"Creating a 'dark' Event for state=%r", state) self._current_snapshot.set_snaphsot(snapshot) # Read the Snapshot into the 'dark' Event stream. yield from bps.stage(self._current_snapshot) yield from bps.trigger_and_read([self._current_snapshot], name=self.stream_name) yield from bps.unstage(self._current_snapshot) self._latch = False if msg is not None: return (yield msg)
def one_nd_step(detectors, step, pos_cache): """ Inner loop of an N-dimensional step scan This is the default function for ``per_step`` param in ND plans. Parameters ---------- detectors : iterable devices to read step : dict mapping motors to positions in this step pos_cache : dict mapping motors to their last-set positions """ def move(): yield from checkpoint() grp = short_uid('set') for motor, pos in step.items(): if pos == pos_cache[motor]: # This step does not move this motor. continue yield from abs_set(motor, pos, group=grp) pos_cache[motor] = pos yield from wait(group=grp) motors = step.keys() yield from move() plt.pause(.001) yield from trigger_and_read(list(detectors) + list(motors))
def one_nd_step(detectors, step, pos_cache): """ Inner loop of an N-dimensional step scan This is the default function for ``per_step`` param in ND plans. Parameters ---------- detectors : iterable devices to read step : dict mapping motors to positions in this step pos_cache : dict mapping motors to their last-set positions """ def move(): yield from checkpoint() grp = short_uid("set") for motor, pos in step.items(): if pos == pos_cache[motor]: # This step does not move this motor. continue yield from abs_set(motor, pos, group=grp) pos_cache[motor] = pos yield from wait(group=grp) motors = step.keys() yield from move() plt.pause(.001) yield from trigger_and_read(list(detectors) + list(motors))
def x_motion_per_step(dets, stream_name): nonlocal last_group if last_group is not None: yield from bps.wait(last_group) yield from bps.trigger_and_read(dets, stream_name) last_group = short_uid() target = start + step_size * (next(j) % num_pos) yield from bps.abs_set(motor, target, group=last_group)
def xpdacq_trigger_and_read(detectors: list, name: str = "primary") -> typing.Generator: """Open shutter, wait, trigger and read detectors, close shutter.""" yield from bps.checkpoint() yield from xb.open_shutter_stub() yield from bps.sleep(xb.glbl["shutter_sleep"]) yield from bps.trigger_and_read(detectors, name=name) yield from xb.close_shutter_stub()
def per_step(detectors, step: dict, pos_cache: dict): _motors = step.keys() yield from my_move_per_step(step, pos_cache) yield from bps.sleep(wait_for_step) yield from open_shutter_stub() yield from bps.sleep(wait_for_shutter) yield from bps.trigger_and_read(list(detectors) + list(_motors)) yield from close_shutter_stub()
def inner(): while True: x = queue.get(timeout=1) if x is None: return yield from step_plan(motors, x) yield from bps.trigger_and_read(dets + motors)
def per_shot(dets): nonlocal start, stop yield from bps.mv(motor.velocity, abs(stop - start) / exposure) gp = short_uid("rocker") yield from bps.abs_set(motor, stop, group=gp) yield from bps.trigger_and_read(dets) yield from bps.wait(group=gp) start, stop = stop, start
def __single_shot(self, gasdelay=0.05, shotdelay=10.0, record=True, use_l3t=False, controls=[], end_run=True): logging.debug("Calling __single_shot with the folling parameters:") logging.debug("gasdelay: {}".format(gasdelay)) logging.debug("shotdelay: {}".format(shotdelay)) logging.debug("record: {}".format(record)) logging.debug("use_l3t: {}".format(use_l3t)) logging.debug("controls: {}".format(controls)) logging.debug("end_run: {}".format(end_run)) nshots = 1 yield from bps.configure(daq, begin_sleep=2, record=record, use_l3t=use_l3t, controls=controls) yield from bps.configure(daq, events=nshots) # Add sequencer, DAQ to detectors for shots dets = [daq, seq] for det in dets: yield from bps.stage(det) # Setup sequencer for requested rate sync_mark = int(self._sync_markers[self._rate]) seq.sync_marker.put(sync_mark) seq.play_mode.put(0) # Run sequence once # Determine the different sequences needed gdelay = int(gasdelay*120) # 120 beam delays/second sdelay = int(shotdelay*120) # 120 beam delays/second slow_cam_seq = [[167, 0, 0, 0]] gas_jet_seq = [[177, 0, 0, 0], [176, gdelay, 0, 0], [169, 0, 0, 0], [0, sdelay, 0, 0]] s = slow_cam_seq + gas_jet_seq logging.debug("Sequence: {}".format(s)) # Get exposure time in beam deltas from number of shots exposure = nshots * (int(shotdelay/120.0) + int(gasdelay/120.0)) logging.debug("Exposure time: {}".format(exposure*120.0)) # Stage and add in slow cameras *after* daq is staged and configured slowcams = SlowCameras() # The camera delay and number of 'during' shots are the same in this case (I think) config = {'slowcamdelay': exposure, 'during': exposure} dets.append(slowcams) # Add this in to auto-unstage later slowcams.stage(config) seq.sequence.put_seq(s) yield from bps.trigger_and_read(dets) # If this is the last move in the scan, check cleanup settings if end_run: daq.end_run()
def gp_inner_plan(): uids = [] while len(queue) > 0: print("*** queue loop") actions = queue.pop() yield from bps.mv(env.action, actions) uid = yield from bps.trigger_and_read([env]) uids.append(uid) return uids
def shutter_step(detectors, motor, step): """ customized step to ensure shutter is open before reading at each motor point and close shutter after reading """ yield from bps.checkpoint() yield from bps.abs_set(motor, step, wait=True) yield from open_shutter_stub() yield from bps.sleep(glbl["shutter_sleep"]) yield from bps.trigger_and_read(list(detectors) + [motor]) yield from close_shutter_stub()
def plan(): while True: for step in np.linspace(start, stop, num): yield from bps.abs_set(motor, step, wait=True) yield from bps.trigger_and_read(list(detectors) + [motor]) yield from bps.checkpoint() err = errorbar(lf.result, 'sigma') if err < err_thresh: break
def test_nonrewindable_detector(RE, hw, start_state, msg_seq): class FakeSig: def get(self): return False hw.det.rewindable = FakeSig() RE.rewindable = start_state m_col = MsgCollector() RE.msg_hook = m_col RE(run_wrapper(trigger_and_read([hw.motor, hw.det]))) assert [m.command for m in m_col.msgs] == msg_seq
def test_plan(det1, det_list): yield from trigger_and_read([det1]) for p in itertools.permutations(det_list): yield from trigger_and_read(det_list)
def plan(dets): data_id = yield from trigger_and_read(dets) data = rt.retrieve_datum(data_id["img"]["value"]) np.testing.assert_allclose(data, np.ones((10, 10)))
def broken_plan(dets): yield from bps.trigger_and_read(dets)
def test_plan(det1, det2): yield from trigger_and_read([det1]) yield from trigger_and_read([det2], name='other')
def test_plan(det1, det2): yield from trigger_and_read([det1]) yield from trigger_and_read([det2])