Fixed types in move_rel method

This commit is contained in:
Joel Collins 2020-12-01 17:10:47 +00:00
parent bc9b80d11a
commit ac667c3e2a

View file

@ -30,11 +30,9 @@ class SangaStage(BaseStage):
self.port = port self.port = port
self.board = Sangaboard(port, **kwargs) self.board = Sangaboard(port, **kwargs)
self._backlash = ( # Initialise backlash storage, used by property setter/getter
None # Initialise backlash storage, used by property setter/getter self._backlash = None
)
self.settle_time = 0.2 # Default move settle time self.settle_time = 0.2 # Default move settle time
self._position_on_enter = None self._position_on_enter = None
@property @property
@ -75,13 +73,16 @@ class SangaStage(BaseStage):
back by ``backlash[i]``. This is computed per-axis, so if some axes are moving back by ``backlash[i]``. This is computed per-axis, so if some axes are moving
in the same direction as ``backlash``, they won't do two moves. in the same direction as ``backlash``, they won't do two moves.
""" """
if self._backlash is not None: if isinstance(self._backlash, (list, np.ndarray)):
return self._backlash return self._backlash
elif isinstance(self._backlash, int):
return np.array([self._backlash] * self.n_axes)
else: else:
return np.array([0] * self.n_axes) return np.array([0] * self.n_axes)
@backlash.setter @backlash.setter
def backlash(self, blsh): def backlash(self, blsh) -> Optional[np.ndarray]:
logging.debug("Setting backlash to %s", (blsh)) logging.debug("Setting backlash to %s", (blsh))
if blsh is None: if blsh is None:
self._backlash = None self._backlash = None
@ -122,11 +123,23 @@ class SangaStage(BaseStage):
displacement: integer or array/list of 3 integers displacement: integer or array/list of 3 integers
axis: None (for 3-axis moves) or one of 'x','y','z' axis: None (for 3-axis moves) or one of 'x','y','z'
backlash: (default: True) whether to correct for backlash. backlash: (default: True) whether to correct for backlash.
Backlash Correction:
This backlash correction strategy ensures we're always approaching the
end point from the same direction, while minimising the amount of extra
motion. It's a good option if you're scanning in a line, for example,
as it will kick in when moving to the start of the line, but not for each
point on the line.
For each axis where we're moving in the *opposite*
direction to self.backlash, we deliberately overshoot:
""" """
with self.lock: with self.lock:
logging.debug("Moving sangaboard by %s", displacement) logging.debug("Moving sangaboard by %s", displacement)
if not backlash or self.backlash is None: if not backlash or self.backlash is None:
return self.board.move_rel(displacement, axis=axis) return self.board.move_rel(displacement, axis=axis)
# If we specify an axis name and a displacement int, convert to a displacement tuple # If we specify an axis name and a displacement int, convert to a displacement tuple
if axis: if axis:
# Displacement MUST be an integer if axis name is specified # Displacement MUST be an integer if axis name is specified
@ -137,32 +150,32 @@ class SangaStage(BaseStage):
# Axis name MUST be x, y, or z # Axis name MUST be x, y, or z
if axis not in ("x", "y", "z"): if axis not in ("x", "y", "z"):
raise ValueError("axis must be one of x, y, or z") raise ValueError("axis must be one of x, y, or z")
move = (
# Create the displacement array
displacement_array: np.ndarray = np.array([
displacement if axis == "x" else 0, displacement if axis == "x" else 0,
displacement if axis == "y" else 0, displacement if axis == "y" else 0,
displacement if axis == "z" else 0, displacement if axis == "z" else 0,
) ])
displacement = move
initial_move = np.array(displacement, dtype=np.int) else:
# Backlash Correction # Convert our displacement tuple/generator into a numpy array
# This backlash correction strategy ensures we're always approaching the displacement_array = np.array(list(displacement))
# end point from the same direction, while minimising the amount of extra
# motion. It's a good option if you're scanning in a line, for example, # Calculate main movement
# as it will kick in when moving to the start of the line, but not for each initial_move: np.ndarray = displacement_array
# point on the line.
# For each axis where we're moving in the *opposite*
# direction to self.backlash, we deliberately overshoot:
initial_move -= np.where( initial_move -= np.where(
self.backlash * displacement < 0, self.backlash * displacement_array < 0,
self.backlash, self.backlash,
np.zeros(self.n_axes, dtype=self.backlash.dtype), np.zeros(self.n_axes, dtype=self.backlash.dtype),
) )
# Make the main movement
self.board.move_rel(initial_move) self.board.move_rel(initial_move)
if np.any(displacement - initial_move != 0): # Handle backlash if required
if np.any(displacement_array - initial_move != 0):
# If backlash correction has kicked in and made us overshoot, move # If backlash correction has kicked in and made us overshoot, move
# to the correct end position (i.e. the move we were asked to make) # to the correct end position (i.e. the move we were asked to make)
self.board.move_rel(displacement - initial_move) self.board.move_rel(displacement_array - initial_move)
# Settle outside of the stage lock so that another move request # Settle outside of the stage lock so that another move request
# can just take over before settling # can just take over before settling
time.sleep(self.settle_time) time.sleep(self.settle_time)