Choosing which of eight directions to walk toward a target, trying the next best when the best is blocked — the chase that makes a pursuer feel its way round corners without finding a path.
{direction, acc} =
Cauldron2D.Steer.chase(acc, current, {target_x - x, target_y - y}, &walk/2, &roll/1)Directions are 0..7, east counting round anticlockwise in eighths, so 2 is +y,
and nil for standing still. walk.(acc, direction) tries a step that way and answers
{:ok, acc} having taken it or {:blocked, acc}. roll.(acc) gives a random 0..255
and the new acc, so the choices follow the game's own random stream.
The pursuer heads diagonally when the target is off both axes, then along the longer
axis, then the shorter (sometimes the other way round, by chance), then the way it was
going, then any direction, and turns back on itself only last. A difference of :slack
or less on an axis counts as none. Default 10.
Summary
Functions
The direction chosen and taken, and the new acc. See the moduledoc.
The direction opposite direction.
The unit step for direction, {dx, dy}; {0.0, 0.0} for nil.
Types
Functions
@spec chase( acc, direction(), {number(), number()}, (acc, 0..7 -> {:ok, acc} | {:blocked, acc}), (acc -> {0..255, acc}), keyword() ) :: {direction(), acc} when acc: term()
The direction chosen and taken, and the new acc. See the moduledoc.
The direction opposite direction.
The unit step for direction, {dx, dy}; {0.0, 0.0} for nil.