in robogym/envs/rearrange/goals/object_state.py [0:0]
def next_goal(self, random_state: RandomState, current_state: dict) -> dict:
"""
Set goal position for each object and get goal dict.
"""
goal_valid, goal_dict = self._update_simulation_for_next_goal(random_state)
target_pos = goal_dict["obj_pos"]
target_rot = goal_dict["obj_rot"]
num_objects = self.mujoco_simulation.num_objects
target_on_table = not self.mujoco_simulation.check_objects_off_table(
target_pos[:num_objects]
).any()
# Compute which of the goals is within the target placement area. Pad this to include
# observations for up to max_num_objects (default to `1.0` for empty slots).
# If an object is out of the placement, the corresponding position in the mask is 0.0.
in_placement_area = self.mujoco_simulation.check_objects_in_placement_area(
target_pos, margin=self.args.mask_margin, soft=self.args.soft_mask
)
assert in_placement_area.shape == (target_pos.shape[0],)
# Create qpos for goal state: based on the current qpos but overwrite the object
# positions to desired positions.
num_objects = self.mujoco_simulation.num_objects
qpos_goal = self.mujoco_simulation.qpos.copy()
for i in range(num_objects):
qpos_idx = self.mujoco_simulation.mj_sim.model.get_joint_qpos_addr(
f"object{i}:joint"
)[0]
qpos_goal[qpos_idx: qpos_idx + 3] = target_pos[i].copy()
qpos_goal[qpos_idx + 3: qpos_idx + 7] = rotation.euler2quat(target_rot[i])
goal_invalid_reason: Optional[str] = None
if not goal_valid:
goal_invalid_reason = "Goal placement is invalid"
elif not target_on_table:
goal_invalid_reason = "Some goal objects are off the table."
goal = {
"obj_pos": target_pos.copy(),
"obj_rot": target_rot.copy(),
"qpos_goal": qpos_goal.copy(),
"goal_valid": goal_valid and target_on_table,
"goal_in_placement_area": in_placement_area.all(),
"goal_objects_in_placement_area": in_placement_area.copy(),
"goal_invalid_reason": goal_invalid_reason,
}
if self.args.rot_dist_type == "icp":
goal["vertices"] = deepcopy(self.mujoco_simulation.get_target_vertices())
goal["icp"] = [
ICP(vertices, error_threshold=self.args.icp_error_threshold)
for vertices in self.mujoco_simulation.get_target_vertices(
# Multiple by 2 because in theory max distance between
# a vertices and it's closest neighbor should be ~edge length / 2.
subdivide_threshold=self.args.icp_error_threshold
* 2
)
]
if self.args.icp_use_bbox_precheck:
goal[
"bounding_box"
] = (
self.mujoco_simulation.get_target_bounding_boxes_in_table_coordinates().copy()
)
return goal