Skip to content

feat(ets): add numerical inverse kinematics for planar ETS2 - #826

Merged
petercorke merged 6 commits into
petercorke:mainfrom
qwist1233-cpu:feat/824-ets2-ikine-lm
Oct 22, 2026
Merged

petercorke merged 6 commits into
petercorke:mainfrom
qwist1233-cpu:feat/824-ets2-ikine-lm

Conversation

@qwist1233-cpu

Copy link
Copy Markdown
Contributor

Summary

ETS2 has fkine, jacob0 and jacobe but no inverse kinematics, so a planar robot built from ET2s can only be solved by hand. This adds ETS2.ikine_LM, the planar counterpart of ETS.ikine_LM:

  • Levenberg-Marquardt with Chan's damping (A = JᵀWeJ + k·E·I), using the existing jacob0.
  • Pose error is the 3-vector (Δx, Δy, Δθ) in the world frame, with the angle wrapped to [-π, π].
  • Same conveniences as the 3D solver: q0 (vector or matrix of starting points), random restarts within the joint limits, mask (e.g. [1, 1, 0] for position only on a 2-link arm), joint_limits rejection, seed, and trajectory input (SE2 with N values or an (N, 3, 3) array). Returns the existing IKSolution dataclass.
  • ikine_LM added to the ETS2 member list in docs/source/arm_ets.rst.

Related issue

Closes #824

How it was verified

New tests/test_ets2_ikine_LM.py (10 tests): 2- and 3-link reach, ndarray target, q0 converging in one search, q0 matrix, mask, joint-limit rejection vs. joint_limits=False, unreachable target, seed reproducibility, trajectory, and ValueError on bad mask / Tep / q0.

$ python -m pytest tests/test_ETS2.py tests/test_ets2_ikine_LM.py tests/test_ETS.py -q
84 passed in 8.31s

Run against the pure-Python kinematics fallback (no compiled extension on this machine), so the C++ fknm path is unchanged and untouched by this PR. ruff format applied to the two touched Python files; the remaining ruff check hits in ETS2.py are pre-existing.

Checklist

  • PR title follows Conventional Commits
  • Tests added and pytest passes
  • Type hints use X | Y, docstring is reST with :param:/:returns:/:raises:
  • AI disclosure: implementation, tests and this description were written with Claude (Anthropic) and reviewed/run by me.

🤖 Generated with Claude Code

@codacy-production

codacy-production Bot commented Oct 17, 2026 •

Copy link
Copy Markdown

Not up to standards ⛔

🔴 Issues 16 high

Alerts:
⚠ 16 issues (≤ 0 issues of at least minor severity)

Results:
16 new issues

Category Results
Security 16 high

View in Codacy

🟢 Metrics 46 complexity · 1 duplication

Metric Results
Complexity 46
Duplication 1

View in Codacy

NEW Get contextual insights on your PRs based on Codacy's metrics, along with PR and Jira context, without leaving GitHub. Enable AI reviewer
TIP This summary will be updated as you push new changes.

@codecov

codecov Bot commented Oct 17, 2026 •

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 0% with 97 lines in your changes missing coverage. Please review.
✅ Project coverage is 0.00%. Comparing base (1c098bd) to head (d3b3d91).
⚠️ Report is 1 commits behind head on main.

Files with missing lines Patch % Lines
src/roboticstoolbox/ets/ETS2.py 0.00% 97 Missing ⚠️
Additional details and impacted files
@@          Coverage Diff          @@
##            main    #826   +/-   ##
=====================================
  Coverage   0.00%   0.00%           
=====================================
  Files        146     146           
  Lines      17103   17200   +97     
=====================================
- Misses     17103   17200   +97     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

ETS2 had fkine, jacob0 and jacobe but no inverse kinematics, so planar
robots could only be solved by hand. Add ETS2.ikine_LM, a Levenberg-
Marquardt solver with Chan's damping (the planar counterpart of
ETS.ikine_LM): 3-vector (x, y, theta) pose error, optional mask, random
restarts within the joint limits, joint-limit rejection and trajectory
support, returning the existing IKSolution dataclass.

Closes petercorke#824

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@qwist1233-cpu
qwist1233-cpu force-pushed the feat/824-ets2-ikine-lm branch from 257f45e to 5eabf27 Compare October 19, 2026 08:11
@qwist1233-cpu

Copy link
Copy Markdown
Contributor Author

Rebased onto main (3b66994) to clear the conflict. One change needed a decision rather than a mechanical resolution:

docs/source/arm_ets.rst is gone since the documentation pass in #833, so the autoclass line this PR edited no longer exists. The equivalent place is now docs/source/ets_2d.rst, and ikine_LM is added there in three spots: the Kinematics autosummary for ETS2, the autoclass :members: list, and the note near the top, which said

ETS2 has no inverse kinematics, Hessian or manipulability methods yet, see Issue 824.

That note is now "ETS2 has numerical inverse kinematics, ikine_LM, but no Hessian or manipulability methods yet" — the issue reference is dropped because this PR closes it, while the Hessian and manipulability gaps stay.

src/roboticstoolbox/ets/ETS2.py merged without conflict; the solver only uses fkine, jacob0, qlim and n, none of which changed in the 18 upstream commits.

Re-verified on the rebased head 5eabf27: pytest tests/test_ets2_ikine_LM.py 10 passed, and tests/test_ets.py 73 passed with 6 subtests, both against this main.

On the Codacy report: the 16 "security" findings are assert statements in tests/test_ets2_ikine_LM.py (Bandit's assert_used), which is how the rest of the test suite is written. Happy to change the style if you prefer something else there.

@petercorke

Copy link
Copy Markdown
Owner

Thank you for the careful rebase and for explaining the ets_2d.rst change so clearly. The solver mirrors the 3D ikine_LM and is a welcome addition, and the tests are good. Codacy's assert warnings are fine: that is how the rest of the test suite is written.

Our own recent changes to ets_2d.rst have caused a new conflict. That's our doing, so I'll resolve it on your branch (you've allowed maintainer edits) and change versionadded to 1.5.0, which is the next release. I'll then merge it.

Resolve the conflict in the ETS2 members list of ets_2d.rst, which main has changed
(swapped, merged), and say versionadded 1.5.0, the next release.

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
@petercorke
petercorke enabled auto-merge (squash) October 21, 2026 07:32
@qwist1233-cpu

Copy link
Copy Markdown
Contributor Author

Sounds good — thanks for taking the ets_2d.rst conflict yourself, and 1.5.0 for the versionadded is right. Maintainer edits are on, so go ahead; ping me if anything else needs changing.

@petercorke
petercorke merged commit aaf0902 into petercorke:main Oct 22, 2026
22 of 23 checks passed
@github-actions github-actions Bot mentioned this pull request Oct 22, 2026
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.

feat(ets): numerical inverse kinematics for planar ETS2

2 participants