Skip to content

feat: add Arrow.FromTo(start, end) classmethod - #41

Merged
petercorke merged 1 commit into
jhavl:mainfrom
petercorke:feat/arrow-fromto
Aug 9, 2026
Merged

feat: add Arrow.FromTo(start, end) classmethod#41
petercorke merged 1 commit into
jhavl:mainfrom
petercorke:feat/arrow-fromto

Conversation

@petercorke

Copy link
Copy Markdown
Collaborator

Summary

  • New Arrow.FromTo(start, end, **kwargs) classmethod -- constructs an
    Arrow spanning two 3-vectors, computing length and pose
    automatically instead of requiring the caller to do it by hand.
  • **kwargs pass straight through to the constructor (color, radius,
    linewidth, head_length, head_radius, ...).
  • Uses SE3.OA(reference, direction) to build the pose, not a delta
    rotation from a fixed reference -- that class of approach (e.g.
    spatialmath's own SE3.RotatedVector) has an antipodal singularity:
    confirmed live that SE3.RotatedVector([0,0,1], [0,0,-1]) currently
    returns identity instead of the correct 180° flip, since the cross
    product used to find the rotation axis is zero right at that point.
    SE3.OA sidesteps this entirely by directly specifying the target
    frame's axes rather than computing a delta from Z. Companion fix
    proposed upstream for the underlying bug:
    bdaiinstitute/spatialmath-python, branch fix/rotatedvector-antipodal
    (PR to follow).
  • reference (the OA "orientation" vector) only needs to be
    non-parallel to direction -- which valid one gets picked is
    irrelevant, since the arrow shaft is rotationally symmetric.
  • Raises ValueError if start == end (direction, and therefore pose,
    would be undefined).

Test plan

  • pytest tests/ -- 172 passed
  • Covers: length/pose correctness across general, axis-aligned, and
    antipodal-to-world-Z directions (proving the antipodal case this PR is
    specifically designed to avoid actually works); coincident-points
    ValueError; kwargs pass-through

Construct an Arrow spanning two points directly, without the caller
having to compute length and pose by hand.

Uses SE3.OA(reference, direction) to build the pose, not a delta
rotation from a fixed reference (e.g. spatialmath's own
SE3.RotatedVector) -- that approach has an antipodal singularity
(direction exactly opposite the reference axis gives a zero-length
cross product), confirmed live it currently returns identity instead
of the correct 180 degree flip. OA sidesteps this entirely by
directly specifying the target frame's axes. Companion fix proposed
upstream: bdaiinstitute/spatialmath-python, branch
fix/rotatedvector-antipodal.

reference (the OA "orientation" vector) only needs to be non-parallel
to direction -- irrelevant which valid one we pick, the arrow shaft is
rotationally symmetric.
@petercorke
petercorke merged commit ce69b8b into jhavl:main Aug 9, 2026
15 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant