Skip to content

Commit 24acadf

Browse files
authored
Fix configure_origin crash on xyz-rpy 6-vector input (#784)
The (6,) branch overwrote the input with np.eye(4) before reading it, so any 6-vector origin raised a broadcast ValueError. Build the matrix with xyzrpy2matrix instead, and cover the path with unit tests.
1 parent 6217309 commit 24acadf

2 files changed

Lines changed: 31 additions & 4 deletions

File tree

skrobot/utils/urdf.py

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
from skrobot.coordinates import normalize_vector
3030
from skrobot.coordinates.math import matrix2ypr
3131
from skrobot.coordinates.math import rpy2matrix
32+
from skrobot.coordinates.math import xyzrpy2matrix
3233
from skrobot.pycompat import lru_cache
3334

3435

@@ -708,10 +709,7 @@ def configure_origin(value):
708709
elif isinstance(value, (list, tuple, np.ndarray)):
709710
value = np.asanyarray(value).astype(np.float64)
710711
if value.shape == (6,):
711-
value = np.eye(4).astype(np.float64)
712-
value[:3, 3] = value[:3]
713-
roll, pitch, yaw = value[3:]
714-
value[:3, :3] = rpy2matrix(roll, pitch, yaw)
712+
value = xyzrpy2matrix(value[:3], value[3:])
715713
elif value.shape != (4, 4):
716714
raise ValueError('Origin must be specified as a 4x4 '
717715
'homogenous transformation matrix')

tests/skrobot_tests/utils_tests/test_urdf.py

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -362,3 +362,32 @@ def test_get_path_with_cache_falls_back_to_env(self):
362362
mock.patch.object(urdf_utils, '_try_rospkg', return_value=None):
363363
assert os.path.samefile(
364364
urdf_utils.get_path_with_cache('my_robot'), share)
365+
366+
367+
class TestConfigureOrigin(unittest.TestCase):
368+
369+
def test_xyzrpy_6vector(self):
370+
# xyz + rpy 6-vector -> 4x4 (this path used to overwrite the input
371+
# with np.eye(4) before reading it and crashed on unpacking)
372+
from skrobot.coordinates.math import rpy2matrix
373+
374+
xyz = [1.0, 2.0, 3.0]
375+
rpy = [0.1, 0.2, 0.3]
376+
matrix = urdf_utils.configure_origin(list(xyz) + list(rpy))
377+
self.assertEqual(matrix.shape, (4, 4))
378+
np.testing.assert_allclose(matrix[:3, 3], xyz)
379+
np.testing.assert_allclose(matrix[:3, :3], rpy2matrix(*rpy))
380+
np.testing.assert_allclose(matrix[3], [0, 0, 0, 1])
381+
382+
def test_none_and_4x4_passthrough(self):
383+
np.testing.assert_allclose(
384+
urdf_utils.configure_origin(None), np.eye(4))
385+
m = np.eye(4)
386+
m[:3, 3] = [4.0, 5.0, 6.0]
387+
np.testing.assert_allclose(urdf_utils.configure_origin(m), m)
388+
389+
def test_invalid_shape_raises(self):
390+
with pytest.raises(ValueError):
391+
urdf_utils.configure_origin(np.zeros(5))
392+
with pytest.raises(TypeError):
393+
urdf_utils.configure_origin('not-a-matrix')

0 commit comments

Comments
 (0)