Fix bug where treedef for mjx.make_data doesn't match mjx.put_data.
PiperOrigin-RevId: 615928973 Change-Id: I08af97ac0300b9d51c1f4b46d48dde98d24197fa
This commit is contained in:
committed by
Copybara-Service
parent
e5811ce2b4
commit
02c62c118c
@@ -10,6 +10,7 @@ MJX
|
|||||||
|
|
||||||
1. Improved performance of SAT for convex collisions.
|
1. Improved performance of SAT for convex collisions.
|
||||||
2. Fixed bug for sphere/capsule-convex deep penetration.
|
2. Fixed bug for sphere/capsule-convex deep penetration.
|
||||||
|
3. Fixed bug where ``mjx.Data`` produced by ``mjx.put_data`` had different treedef than ``mjx.make_data``.
|
||||||
|
|
||||||
Version 3.1.3 (March 5th, 2024)
|
Version 3.1.3 (March 5th, 2024)
|
||||||
-----------------------------------
|
-----------------------------------
|
||||||
|
|||||||
@@ -172,7 +172,7 @@ def make_data(m: Union[types.Model, mujoco.MjModel]) -> types.Data:
|
|||||||
ctrl=zero_nu,
|
ctrl=zero_nu,
|
||||||
qfrc_applied=zero_nv,
|
qfrc_applied=zero_nv,
|
||||||
xfrc_applied=zero_nbody_6,
|
xfrc_applied=zero_nbody_6,
|
||||||
eq_active=jp.zeros(m.neq, dtype=int),
|
eq_active=jp.zeros(m.neq, dtype=jp.uint8),
|
||||||
qacc=zero_nv,
|
qacc=zero_nv,
|
||||||
act_dot=zero_na,
|
act_dot=zero_na,
|
||||||
xpos=zero_nbody_3,
|
xpos=zero_nbody_3,
|
||||||
@@ -374,6 +374,9 @@ def put_data(m: mujoco.MjModel, d: mujoco.MjData, device=None) -> types.Data:
|
|||||||
for fname in ('xmat', 'ximat', 'geom_xmat', 'site_xmat', 'cam_xmat'):
|
for fname in ('xmat', 'ximat', 'geom_xmat', 'site_xmat', 'cam_xmat'):
|
||||||
fields[fname] = fields[fname].reshape((-1, 3, 3))
|
fields[fname] = fields[fname].reshape((-1, 3, 3))
|
||||||
|
|
||||||
|
# MJX does not support islanding, so only transfer the first solver_niter
|
||||||
|
fields['solver_niter'] = fields['solver_niter'][0]
|
||||||
|
|
||||||
# pad efc fields: MuJoCo efc arrays are sparse for inactive constraints.
|
# pad efc fields: MuJoCo efc arrays are sparse for inactive constraints.
|
||||||
# efc_J is also optionally column-sparse (typically for large nv). MJX is
|
# efc_J is also optionally column-sparse (typically for large nv). MJX is
|
||||||
# neither: it contains zeros for inactive constraints, and efc_J is always
|
# neither: it contains zeros for inactive constraints, and efc_J is always
|
||||||
|
|||||||
@@ -434,5 +434,20 @@ class DataIOTest(parameterized.TestCase):
|
|||||||
self.assertEqual(d_2.contact.frame.shape, (1, 9))
|
self.assertEqual(d_2.contact.frame.shape, (1, 9))
|
||||||
np.testing.assert_allclose(d_2.contact.frame, d.contact.frame)
|
np.testing.assert_allclose(d_2.contact.frame, d.contact.frame)
|
||||||
|
|
||||||
|
def test_make_matches_put(self):
|
||||||
|
"""Test that make_data produces a pytree that matches put_data."""
|
||||||
|
|
||||||
|
m = mujoco.MjModel.from_xml_string(_MULTIPLE_CONSTRAINTS)
|
||||||
|
d = mujoco.MjData(m)
|
||||||
|
mujoco.mj_step(m, d, 2)
|
||||||
|
dx = mjx.put_data(m, d)
|
||||||
|
|
||||||
|
step_fn = lambda d: d.replace(time=d.time + 1)
|
||||||
|
step_fn_jit = jax.jit(step_fn).lower(dx).compile()
|
||||||
|
|
||||||
|
# placing an MjData onto device should yield the same treedef mjx.Data as
|
||||||
|
# calling make_data. they should be interchangeable for jax functions:
|
||||||
|
step_fn_jit(mjx.make_data(m))
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
absltest.main()
|
absltest.main()
|
||||||
|
|||||||
Reference in New Issue
Block a user