Skip to content

Commit b22e60a

Browse files
authored
Merge pull request #650 from StanfordVL/fix-primitives-2
Fix primitives for navigate, grasp and place
2 parents 4c5df20 + db89187 commit b22e60a

File tree

7 files changed

+129
-136
lines changed

7 files changed

+129
-136
lines changed

omnigibson/action_primitives/starter_semantic_action_primitives.py

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
from functools import cached_property
99
import inspect
1010
import logging
11+
import random
1112
from aenum import IntEnum, auto
1213
from math import ceil
1314
import cv2
@@ -60,7 +61,7 @@
6061
m.MAX_CARTESIAN_HAND_STEP = 0.002
6162
m.MAX_STEPS_FOR_HAND_MOVE_JOINT = 500
6263
m.MAX_STEPS_FOR_HAND_MOVE_IK = 1000
63-
m.MAX_STEPS_FOR_GRASP_OR_RELEASE = 30
64+
m.MAX_STEPS_FOR_GRASP_OR_RELEASE = 250
6465
m.MAX_STEPS_FOR_WAYPOINT_NAVIGATION = 500
6566
m.MAX_ATTEMPTS_FOR_OPEN_CLOSE = 20
6667

@@ -274,7 +275,8 @@ def __init__(self, env, add_context=False, enable_head_tracking=True, always_tra
274275

275276
def _postprocess_action(self, action):
276277
"""Postprocesses action by applying head tracking and adding context if necessary."""
277-
action = self._overwrite_head_action(action)
278+
if self._enable_head_tracking:
279+
action = self._overwrite_head_action(action)
278280

279281
if not self.add_context:
280282
return action
@@ -646,7 +648,7 @@ def _grasp(self, obj):
646648

647649
# Allow grasping from suboptimal extents if we've tried enough times.
648650
grasp_poses = get_grasp_poses_for_object_sticky(obj)
649-
grasp_pose, object_direction = np.random.choice(grasp_poses)
651+
grasp_pose, object_direction = random.choice(grasp_poses)
650652

651653
# Prepare data for the approach later.
652654
approach_pos = grasp_pose[0] + object_direction * m.GRASP_APPROACH_DISTANCE
@@ -836,7 +838,7 @@ def _manipulation_control_idx(self):
836838
return np.concatenate([self.robot.trunk_control_idx, self.robot.arm_control_idx[self.arm]])
837839

838840
# Otherwise just return the default arm control idx
839-
return self.robot.arm_control_idx[self.arm]
841+
return np.concatenate([self.robot.trunk_control_idx, self.robot.arm_control_idx[self.arm]])
840842

841843
@cached_property
842844
def _manipulation_descriptor_path(self):
@@ -1051,7 +1053,7 @@ def _move_hand_direct_ik(self, target_pose, stop_on_contact=False, ignore_failur
10511053
# make sure controller is InverseKinematicsController and in expected mode
10521054
controller_config = self.robot._controller_config["arm_" + self.arm]
10531055
assert controller_config["name"] == "InverseKinematicsController", "Controller must be InverseKinematicsController"
1054-
assert controller_config["mode"] == "pose_absolute_ori", "Controller must be in pose_delta_ori mode"
1056+
assert controller_config["mode"] == "pose_absolute_ori", "Controller must be in pose_absolute_ori mode"
10551057
if in_world_frame:
10561058
target_pose = self._get_pose_in_robot_frame(target_pose)
10571059
target_pos = target_pose[0]
@@ -1325,7 +1327,7 @@ def _empty_action(self):
13251327
action[action_idx] = self.robot.get_joint_positions()[joint_idx]
13261328
elif self.robot._controller_config[name]["name"] == "InverseKinematicsController":
13271329
# overwrite the goal orientation, since it is in absolute frame.
1328-
assert self.robot._controller_config["arm_" + self.arm]["mode"] == "pose_absolute_ori", "Controller must be in pose_delta_ori mode"
1330+
assert self.robot._controller_config["arm_" + self.arm]["mode"] == "pose_absolute_ori", "Controller must be in pose_absolute_ori mode"
13291331
current_quat = self.robot.get_relative_eef_orientation()
13301332
current_ori = T.quat2axisangle(current_quat)
13311333
control_idx = self.robot.controller_action_idx["arm_" + self.arm]
@@ -1363,7 +1365,7 @@ def _get_reset_eef_pose(self):
13631365
if self.robot_model == "Tiago":
13641366
return np.array([0.28493954, 0.37450749, 1.1512334]), np.array([-0.21533823, 0.05361032, -0.08631776, 0.97123871])
13651367
else:
1366-
raise NotImplementedError
1368+
return np.array([ 0.48688125, -0.12507881, 0.97888719]), np.array([ 0.61324748, 0.61305553, -0.35266518, 0.35173529])
13671369

13681370
def _get_reset_joint_pos(self):
13691371
reset_pose_fetch = np.array(

omnigibson/configs/tiago_primitives.yaml renamed to omnigibson/configs/fetch_primitives.yaml

Lines changed: 13 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
env:
2-
action_frequency: 60 # (int): environment executes action at the action_frequency rate
3-
physics_frequency: 60 # (int): physics frequency (1 / physics_timestep for physx)
2+
action_frequency: 30 # (int): environment executes action at the action_frequency rate
3+
physics_frequency: 120 # (int): physics frequency (1 / physics_timestep for physx)
44
device: null # (None or str): specifies the device to be used if running on the gpu with torch backend
55
automatic_reset: false # (bool): whether to automatic reset after an episode finishes
66
flatten_action_space: false # (bool): whether to flatten the action space as a sinle 1D-array
@@ -31,8 +31,7 @@ scene:
3131
include_robots: false
3232

3333
robots:
34-
- name: tiago
35-
type: Tiago
34+
- type: Fetch
3635
obs_modalities: [scan, rgb, depth]
3736
scale: 1.0
3837
self_collisions: true
@@ -44,40 +43,24 @@ robots:
4443
default_arm_pose: diagonal30
4544
controller_config:
4645
base:
47-
name: JointController
48-
motor_type: velocity
49-
arm_left:
50-
name: InverseKinematicsController
51-
motor_type: velocity
52-
command_input_limits: null
53-
command_output_limits: null
54-
mode : pose_absolute_ori
55-
kv: 3.0
56-
arm_right:
46+
name: DifferentialDriveController
47+
arm_0:
5748
name: InverseKinematicsController
58-
motor_type: velocity
59-
command_input_limits: null
60-
command_output_limits: null
61-
mode : pose_absolute_ori
62-
kv: 3.0
63-
gripper_left:
64-
name: JointController
65-
motor_type: position
66-
command_input_limits: [-1, 1]
67-
command_output_limits: null
68-
use_delta_commands: true
69-
gripper_right:
49+
command_input_limits: default
50+
command_output_limits:
51+
- [-0.2, -0.2, -0.2, -0.5, -0.5, -0.5]
52+
- [0.2, 0.2, 0.2, 0.5, 0.5, 0.5]
53+
mode: pose_absolute_ori
54+
kp: 300.0
55+
gripper_0:
7056
name: JointController
7157
motor_type: position
7258
command_input_limits: [-1, 1]
7359
command_output_limits: null
7460
use_delta_commands: true
7561
camera:
7662
name: JointController
77-
motor_type: position
78-
command_input_limits: null
79-
command_output_limits: null
80-
use_delta_commands: false
63+
use_delta_commands: False
8164

8265
objects: []
8366

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
import os
2+
import yaml
3+
import numpy as np
4+
5+
import omnigibson as og
6+
from omnigibson.macros import gm
7+
from omnigibson.action_primitives.starter_semantic_action_primitives import StarterSemanticActionPrimitives, StarterSemanticActionPrimitiveSet
8+
9+
# Don't use GPU dynamics and use flatcache for performance boost
10+
# gm.USE_GPU_DYNAMICS = True
11+
# gm.ENABLE_FLATCACHE = True
12+
13+
def execute_controller(ctrl_gen, env):
14+
for action in ctrl_gen:
15+
env.step(action)
16+
17+
def main():
18+
"""
19+
Demonstrates how to use the action primitives to pick and place an object in a crowded scene.
20+
21+
It loads Rs_int with a Fetch robot, and the robot picks and places an apple.
22+
"""
23+
# Load the config
24+
config_filename = os.path.join(og.example_config_path, "fetch_primitives.yaml")
25+
config = yaml.load(open(config_filename, "r"), Loader=yaml.FullLoader)
26+
27+
# Update it to run a grocery shopping task
28+
config["scene"]["scene_model"] = "Rs_int"
29+
config["scene"]["not_load_object_categories"] = ["ceilings"]
30+
config["objects"] = [
31+
{
32+
"type": "DatasetObject",
33+
"name": "apple",
34+
"category": "apple",
35+
"model": "agveuv",
36+
"position": [-0.3, -1.1, 0.5],
37+
"orientation": [0, 0, 0, 1]
38+
},
39+
]
40+
41+
# Load the environment
42+
env = og.Environment(configs=config)
43+
scene = env.scene
44+
robot = env.robots[0]
45+
46+
# Allow user to move camera more easily
47+
og.sim.enable_viewer_camera_teleoperation()
48+
49+
controller = StarterSemanticActionPrimitives(env, enable_head_tracking=False)
50+
cabinet = scene.object_registry("name", "bottom_cabinet_slgzfc_0")
51+
apple = scene.object_registry("name", "apple")
52+
53+
# Grasp apple
54+
print("Executing controller")
55+
execute_controller(controller.apply_ref(StarterSemanticActionPrimitiveSet.GRASP, apple), env)
56+
print("Finished executing grasp")
57+
58+
# Place on cabinet
59+
print("Executing controller")
60+
execute_controller(controller.apply_ref(StarterSemanticActionPrimitiveSet.PLACE_ON_TOP, cabinet), env)
61+
print("Finished executing place")
62+
63+
if __name__ == "__main__":
64+
main()

omnigibson/examples/action_primitives/solve_simple_task.py

Lines changed: 7 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
"""
2-
Example script demo'ing robot primitive to solve a task
3-
"""
41
import os
52
import yaml
63
import numpy as np
@@ -17,22 +14,14 @@ def execute_controller(ctrl_gen, env):
1714
for action in ctrl_gen:
1815
env.step(action)
1916

20-
def set_start_pose(robot):
21-
reset_pose_tiago = np.array([
22-
-1.78029833e-04, 3.20231302e-05, -1.85759447e-07, -1.16488536e-07,
23-
4.55182843e-08, 2.36128806e-04, 1.50000000e-01, 9.40000000e-01,
24-
-1.10000000e+00, 0.00000000e+00, -0.90000000e+00, 1.47000000e+00,
25-
0.00000000e+00, 2.10000000e+00, 2.71000000e+00, 1.50000000e+00,
26-
1.71000000e+00, 1.30000000e+00, -1.57000000e+00, -1.40000000e+00,
27-
1.39000000e+00, 0.00000000e+00, 0.00000000e+00, 4.50000000e-02,
28-
4.50000000e-02, 4.50000000e-02, 4.50000000e-02,
29-
])
30-
robot.set_joint_positions(reset_pose_tiago)
31-
og.sim.step()
32-
3317
def main():
18+
"""
19+
Demonstrates how to use the action primitives to pick and place an object in an empty scene.
20+
21+
It loads Rs_int with a Fetch robot, and the robot picks and places a bottle of cologne.
22+
"""
3423
# Load the config
35-
config_filename = os.path.join(og.example_config_path, "tiago_primitives.yaml")
24+
config_filename = os.path.join(og.example_config_path, "fetch_primitives.yaml")
3625
config = yaml.load(open(config_filename, "r"), Loader=yaml.FullLoader)
3726

3827
# Update it to create a custom environment and run some actions
@@ -66,8 +55,7 @@ def main():
6655
# Allow user to move camera more easily
6756
og.sim.enable_viewer_camera_teleoperation()
6857

69-
controller = StarterSemanticActionPrimitives(env)
70-
set_start_pose(robot)
58+
controller = StarterSemanticActionPrimitives(env, enable_head_tracking=False)
7159

7260
# Grasp of cologne
7361
grasp_obj = scene.object_registry("name", "cologne")

omnigibson/examples/action_primitives/wip_solve_behavior_task.py

Lines changed: 8 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
"""
2-
Example script demo'ing robot primitive to solve a task
3-
"""
41
import os
52
import yaml
63
import numpy as np
@@ -17,22 +14,15 @@ def execute_controller(ctrl_gen, env):
1714
for action in ctrl_gen:
1815
env.step(action)
1916

20-
def set_start_pose(robot):
21-
reset_pose_tiago = np.array([
22-
-1.78029833e-04, 3.20231302e-05, -1.85759447e-07, -1.16488536e-07,
23-
4.55182843e-08, 2.36128806e-04, 1.50000000e-01, 9.40000000e-01,
24-
-1.10000000e+00, 0.00000000e+00, -0.90000000e+00, 1.47000000e+00,
25-
0.00000000e+00, 2.10000000e+00, 2.71000000e+00, 1.50000000e+00,
26-
1.71000000e+00, 1.30000000e+00, -1.57000000e+00, -1.40000000e+00,
27-
1.39000000e+00, 0.00000000e+00, 0.00000000e+00, 4.50000000e-02,
28-
4.50000000e-02, 4.50000000e-02, 4.50000000e-02,
29-
])
30-
robot.set_joint_positions(reset_pose_tiago)
31-
og.sim.step()
32-
3317
def main():
18+
"""
19+
Demonstrates how to use the action primitives to solve a simple BEHAVIOR-1K task.
20+
21+
It loads Benevolence_1_int with a Fetch robot, and the robot attempts to solve the
22+
picking_up_trash task using a hardcoded sequence of primitives.
23+
"""
3424
# Load the config
35-
config_filename = os.path.join(og.example_config_path, "tiago_primitives.yaml")
25+
config_filename = os.path.join(og.example_config_path, "fetch_primitives.yaml")
3626
config = yaml.load(open(config_filename, "r"), Loader=yaml.FullLoader)
3727

3828
# Update it to run a grocery shopping task
@@ -56,8 +46,7 @@ def main():
5646
# Allow user to move camera more easily
5747
og.sim.enable_viewer_camera_teleoperation()
5848

59-
controller = StarterSemanticActionPrimitives(env)
60-
set_start_pose(robot)
49+
controller = StarterSemanticActionPrimitives(env, enable_head_tracking=False)
6150

6251
# Grasp can of soda
6352
grasp_obj = scene.object_registry("name", "can_of_soda_89")

omnigibson/utils/motion_planning_utils.py

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,9 @@ def get_angle_between_poses(p1, p2):
105105
return np.arctan2(segment[1], segment[0])
106106

107107
def create_state(space, x, y, yaw):
108+
x = float(x)
109+
y = float(y)
110+
yaw = float(yaw)
108111
state = ob.State(space)
109112
state().setX(x)
110113
state().setY(y)
@@ -260,12 +263,8 @@ def state_valid_fn(q):
260263
end_conf[i] = joint.upper_limit
261264
if end_conf[i] < joint.lower_limit:
262265
end_conf[i] = joint.lower_limit
263-
if joint.upper_limit - joint.lower_limit > 2 * np.pi:
264-
bounds.setLow(i, 0.0)
265-
bounds.setHigh(i, 2 * np.pi)
266-
else:
267-
bounds.setLow(i, float(joint.lower_limit))
268-
bounds.setHigh(i, float(joint.upper_limit))
266+
bounds.setLow(i, float(joint.lower_limit))
267+
bounds.setHigh(i, float(joint.upper_limit))
269268
space.setBounds(bounds)
270269

271270
# create a simple setup object

0 commit comments

Comments
 (0)