def _extractPos(self, hkle): ki = self._attached_mono.read(0) kf = self._attached_ana.read(0) if self.inelastic: if self.emode == 'FKI': kf = ki - hkle[3] else: ki = kf + hkle[3] ki = to_k(ki, self._attached_mono.unit) kf = to_k(kf, self._attached_ana.unit) qepos = tasQEPosition(ki, kf, hkle[0], hkle[1], hkle[2], 0) ub = session.experiment.sample.getUB() try: angpos = calcTasQAngles(ub, np.array(self.plane_normal), self.scattering_sense, 0, qepos) except RuntimeError as xx: raise InvalidValueError(xx) from None poslist = [('a3', angpos.a3), ('a4', angpos.sample_two_theta)] if self.inelastic: poslist.append(('mono', from_k(ki, self._attached_mono.unit))) poslist.append(('ana', from_k(kf, self._attached_ana.unit))) if self.out_of_plane: poslist.append(('sgu', angpos.sgu)) poslist.append(('sgl', angpos.sgl)) return poslist
def doUpdateUnit(self, value): if 'unit' not in self._params: # this is the initial update return if self._mode not in (MASTER, SIMULATION): # change limits only from the master copy, or in simulation mode return new_absmin = from_k(to_k(self.abslimits[0], self.unit), value) new_absmax = from_k(to_k(self.abslimits[1], self.unit), value) if new_absmin > new_absmax: new_absmin, new_absmax = new_absmax, new_absmin self._setROParam('abslimits', (new_absmin, new_absmax)) if self.userlimits != (0, 0): new_umin = from_k(to_k(self.userlimits[0], self.unit), value) new_umax = from_k(to_k(self.userlimits[1], self.unit), value) if new_umin > new_umax: new_umin, new_umax = new_umax, new_umin new_umin = max(new_umin, new_absmin) new_umax = min(new_umax, new_absmax) self.userlimits = (new_umin, new_umax) if 'target' in self._params and self.target and self.target != 'unknown': # this should be still within the limits self._setROParam('target', from_k(to_k(self.target, self.unit), value)) self.read(0)
def _readPos(self, maxage=0): ki = to_k(self._attached_mono.read(maxage), self._attached_mono.unit) kf = to_k(self._attached_ana.read(maxage), self._attached_ana.unit) a3 = self._attached_a3.read(maxage) sample_two_theta = self._attached_a4.read(maxage) sgu = self._attached_sgu.read(maxage) sgl = self._attached_sgl.read(maxage) return ki, kf, a3, sample_two_theta, sgu, sgl
def _movefoci(self, focmode, hfocuspars, vfocuspars): lam = from_k(to_k(self.target, self.unit), 'A') # get goalposition in A focusv, focush = self._attached_focusv, self._attached_focush if focmode == 'flat': if focusv: focusv.move(self.vfocusflat) if focush: focush.move(self.hfocusflat) elif focmode == 'horizontal': if focusv: focusv.move(self.vfocusflat) if focush: focush.move(self._calfocus(lam, hfocuspars)) elif focmode == 'vertical': if focusv: focusv.move(self._calfocus(lam, vfocuspars)) if focush: focush.move(self.hfocusflat) elif focmode == 'double': if focusv: focusv.move(self._calfocus(lam, vfocuspars)) if focush: focush.move(self._calfocus(lam, hfocuspars)) else: if self._focwarnings and (focusv or focush): self.log.warning('focus is in manual mode') self._focwarnings -= 1
def _adjust(self, newvalue, unit): """Adjust the offsets of theta and twotheta to let the device value match the given value. """ th, tt = self._calc_angles(to_k(newvalue, unit)) thdiff = self._attached_theta.read(0) - th ttdiff = self._attached_twotheta.read(0) - tt self._attached_theta.offset += thdiff self._attached_twotheta.offset += ttdiff
def doIsAllowed(self, pos): try: theta = thetaangle(self.dvalue, self.order, to_k(pos, self.unit)) except ValueError: return False, 'wavelength not reachable with d=%.3f A and n=%s' % \ (self.dvalue, self.order) ttvalue = 2.0 * self.scatteringsense * theta ttdev = self._attached_twotheta ok, why = ttdev.isAllowed(ttvalue) if not ok: return ok, '[%s] moving to %s, ' % ( ttdev, ttdev.format(ttvalue, unit=True)) + why return True, ''
def doReadPrecision(self): if not hasattr(self, 'scatteringsense'): # object not yet intialized return 0 # the precision depends on the angular precision of theta and twotheta val = self.read() if val == 0.0: return 0.0 lam = from_k(to_k(val, self.unit), 'A') dtheta = self._attached_theta.precision + \ self._attached_twotheta.precision dlambda = abs(2.0 * self.dvalue * cos(self._attached_twotheta.read() * pi / 360) * dtheta / 180 * pi) if self.unit == 'A-1': return 2 * pi / lam**2 * dlambda elif self.unit == 'meV': return 2 * ANG2MEV / lam**3 * dlambda elif self.unit == 'THz': return 2 * ANG2MEV / THZ2MEV / lam**3 * dlambda return dlambda
def doStart(self, pos): th, tt = self._calc_angles(to_k(pos, self.unit)) self._attached_twotheta.start(tt) self._attached_theta.start(th) self._movefoci(self.focmode, self.hfocuspars, self.vfocuspars) self._sim_setValue(pos)
def _movefoci(self, focmode, hfocuspars, vfocuspars): focusv = self._attached_focusv if focusv: focusv.move( self._calfocus(from_k(to_k(self.target, self.unit), 'A'), vfocuspars))
def _createPos(self, ei, ef, a3, a4, sgu, sgl): return to_k(ei, 'meV'), to_k(ef, 'meV'), a3, a4, sgu, sgl