Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion source/extensions/omni.isaac.lab/config/extension.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
[package]

# Note: Semantic Versioning is used: https://semver.org/
version = "0.27.22"
version = "0.27.23"

# Description
title = "Isaac Lab framework for Robot Learning"
Expand Down
10 changes: 10 additions & 0 deletions source/extensions/omni.isaac.lab/docs/CHANGELOG.rst
Original file line number Diff line number Diff line change
@@ -1,6 +1,16 @@
Changelog
---------

0.27.23 (2024-12-06)
~~~~~~~~~~~~~~~~~~~~

Fixed
^^^^^

* Fixed the enforcement of :attr:`~omni.isaac.lab.actuators.ActuatorBaseCfg.velocity_limits` at the
:attr:`~omni.isaac.lab.assets.Articulation.root_physx_view` level.


0.27.22 (2024-12-06)
~~~~~~~~~~~~~~~~~~~~

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -424,6 +424,39 @@ def write_joint_damping_to_sim(
# set into simulation
self.root_physx_view.set_dof_dampings(self._data.joint_damping.cpu(), indices=physx_env_ids.cpu())

def write_joint_velocity_limit_to_sim(
self,
limits: torch.Tensor | float,
joint_ids: Sequence[int] | slice | None = None,
env_ids: Sequence[int] | None = None,
):
"""Write joint max velocity to the simulation.

Args:
limits: Joint max velocity. Shape is (len(env_ids), len(joint_ids)).
joint_ids: The joint indices to set the max velocity for. Defaults to None (all joints).
env_ids: The environment indices to set the max velocity for. Defaults to None (all environments).
"""
# resolve indices
physx_env_ids = env_ids
if env_ids is None:
env_ids = slice(None)
physx_env_ids = self._ALL_INDICES
if joint_ids is None:
joint_ids = slice(None)
# broadcast env_ids if needed to allow double indexing
if env_ids != slice(None) and joint_ids != slice(None):
env_ids = env_ids[:, None]
# move tensor to cpu if needed
if isinstance(limits, torch.Tensor):
limits = limits.to(self.device)

# set into internal buffers
self._data.joint_velocity_limits = self.root_physx_view.get_dof_max_velocities().to(self.device)
self._data.joint_velocity_limits[env_ids, joint_ids] = limits
# set into simulation
self.root_physx_view.set_dof_max_velocities(self._data.joint_velocity_limits.cpu(), indices=physx_env_ids.cpu())

def write_joint_effort_limit_to_sim(
self,
limits: torch.Tensor | float,
Expand Down Expand Up @@ -1158,6 +1191,7 @@ def _process_actuators_cfg(self):
self.write_joint_stiffness_to_sim(actuator.stiffness, joint_ids=actuator.joint_indices)
self.write_joint_damping_to_sim(actuator.damping, joint_ids=actuator.joint_indices)
self.write_joint_effort_limit_to_sim(actuator.effort_limit, joint_ids=actuator.joint_indices)
self.write_joint_velocity_limit_to_sim(actuator.velocity_limit, joint_ids=actuator.joint_indices)
self.write_joint_armature_to_sim(actuator.armature, joint_ids=actuator.joint_indices)
self.write_joint_friction_to_sim(actuator.friction, joint_ids=actuator.joint_indices)
else:
Expand All @@ -1166,6 +1200,7 @@ def _process_actuators_cfg(self):
self.write_joint_stiffness_to_sim(0.0, joint_ids=actuator.joint_indices)
self.write_joint_damping_to_sim(0.0, joint_ids=actuator.joint_indices)
self.write_joint_effort_limit_to_sim(1.0e9, joint_ids=actuator.joint_indices)
self.write_joint_velocity_limit_to_sim(actuator.velocity_limit, joint_ids=actuator.joint_indices)
self.write_joint_armature_to_sim(actuator.armature, joint_ids=actuator.joint_indices)
self.write_joint_friction_to_sim(actuator.friction, joint_ids=actuator.joint_indices)
# Store the actual default stiffness and damping values for explicit actuators (not written the sim)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -220,6 +220,9 @@ def update(self, dt: float):
joint_limits: torch.Tensor = None
"""Joint limits provided to simulation. Shape is (num_instances, num_joints, 2)."""

joint_velocity_limits: torch.Tensor = None
"""Joint maximum velocity provided to simulation. Shape is (num_instances, num_joints)."""

##
# Fixed tendon properties.
##
Expand Down
43 changes: 41 additions & 2 deletions source/extensions/omni.isaac.lab/test/assets/test_articulation.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@ def generate_articulation_cfg(
articulation_type: Literal["humanoid", "panda", "anymal", "shadow_hand", "single_joint"],
stiffness: float | None = 10.0,
damping: float | None = 2.0,
vel_limit: float | None = 100.0,
effort_limit: float | None = 400.0,
) -> ArticulationCfg:
"""Generate an articulation configuration.

Expand Down Expand Up @@ -72,8 +74,8 @@ def generate_articulation_cfg(
actuators={
"joint": ImplicitActuatorCfg(
joint_names_expr=[".*"],
effort_limit=400.0,
velocity_limit=100.0,
effort_limit=effort_limit,
velocity_limit=vel_limit,
stiffness=0.0,
damping=10.0,
),
Expand Down Expand Up @@ -813,6 +815,43 @@ def test_setting_gains_from_cfg_dict(self):
torch.testing.assert_close(articulation.actuators["body"].stiffness, expected_stiffness)
torch.testing.assert_close(articulation.actuators["body"].damping, expected_damping)

def test_setting_velocity_limits(self):
"""Test that velocity limits are loaded form the configuration correctly."""
for num_articulations in (1, 2):
for device in ("cuda:0", "cpu"):
for limit in (5.0, None):
with self.subTest(num_articulations=num_articulations, device=device, limit=limit):
with build_simulation_context(
device=device, add_ground_plane=False, auto_add_lighting=True
) as sim:
articulation_cfg = generate_articulation_cfg(
articulation_type="single_joint", vel_limit=limit, effort_limit=limit
)
articulation, _ = generate_articulation(
articulation_cfg=articulation_cfg, num_articulations=num_articulations, device=device
)
# Play sim
sim.reset()

if limit is not None:
# Expected gains
expected_velocity_limit = torch.full(
(articulation.num_instances, articulation.num_joints),
limit,
device=articulation.device,
)
# Check that gains are loaded from USD file
torch.testing.assert_close(
articulation.actuators["joint"].velocity_limit, expected_velocity_limit
)
torch.testing.assert_close(
articulation.data.joint_velocity_limits, expected_velocity_limit
)
torch.testing.assert_close(
articulation.root_physx_view.get_dof_max_velocities().to(device),
expected_velocity_limit,
)

def test_reset(self):
"""Test that reset method works properly.

Expand Down
Loading