@@ -96,17 +96,23 @@ def CreatePlannerParametersString(options, params=None,
96
96
97
97
return lxml .etree .tostring (params_xml )
98
98
99
+ def HasGroup (cspec , group_name ):
100
+ try :
101
+ cspec .GetGroupFromName (group_name )
102
+ return True
103
+ except openravepy .openrave_exception :
104
+ return False
105
+
99
106
def HasAffineDOFs (cspec ):
100
- def has_group (cspec , group_name ):
101
- try :
102
- cspec .GetGroupFromName (group_name )
103
- return True
104
- except openravepy .openrave_exception :
105
- return False
107
+ return (HasGroup (cspec , 'affine_transform' )
108
+ or HasGroup (cspec , 'affine_velocities' )
109
+ or HasGroup (cspec , 'affine_accelerations' ))
106
110
107
- return (has_group (cspec , 'affine_transform' )
108
- or has_group (cspec , 'affine_velocities' )
109
- or has_group (cspec , 'affine_accelerations' ))
111
+ def HasJointDOFs (cspec ):
112
+ return (HasGroup (cspec , 'joint_values' )
113
+ or HasGroup (cspec , 'joint_velocities' )
114
+ or HasGroup (cspec , 'joint_accelerations' )
115
+ or HasGroup (cspec , 'joint_torques' ))
110
116
111
117
def GetTrajectoryIndices (traj ):
112
118
try :
@@ -689,28 +695,58 @@ def IsAtTrajectoryStart(robot, trajectory):
689
695
@returns: True if the robot's active DOFs match the given trajectory
690
696
False if one or more active DOFs differ by DOF resolution
691
697
"""
692
- # Get used indices and starting configuration from trajectory.
693
698
cspec = trajectory .GetConfigurationSpecification ()
694
- dof_indices , _ = cspec .ExtractUsedIndices (robot )
695
- traj_values = cspec .ExtractJointValues (
696
- trajectory .GetWaypoint (0 ), robot , dof_indices )
697
-
698
- # Get current configuration of robot for used indices.
699
- with robot .GetEnv ():
700
- robot_values = robot .GetDOFValues (dof_indices )
701
- dof_resolutions = robot .GetDOFResolutions (dof_indices )
702
-
703
- # Check deviation in each DOF, using OpenRAVE's SubtractValue function.
704
- dof_infos = zip (dof_indices , traj_values , robot_values , dof_resolutions )
705
- for dof_index , traj_value , robot_value , dof_resolution in dof_infos :
706
- # Look up the Joint and Axis of the DOF from the robot.
707
- joint = robot .GetJointFromDOFIndex (dof_index )
708
- axis = dof_index - joint .GetDOFIndex ()
709
-
710
- # If any joint deviates too much, return False.
711
- delta_value = abs (joint .SubtractValue (traj_value , robot_value , axis ))
712
- if delta_value > dof_resolution :
699
+ needs_base = HasAffineDOFs (cspec )
700
+ needs_joints = HasJointDOFs (cspec )
701
+
702
+ if needs_base and needs_joints :
703
+ raise ValueError ('Trajectories with affine and joint DOFs are not supported' )
704
+
705
+ if trajectory .GetEnv () != robot .GetEnv ():
706
+ raise ValueError ('The environment attached to the trajectory does not match the environment attached to the robot' )
707
+
708
+ if needs_base :
709
+ doft = openravepy .DOFAffine .X | openravepy .DOFAffine .Y | openravepy .DOFAffine .RotationAxis
710
+ current_pose = openravepy .RaveGetAffineDOFValuesFromTransform (robot .GetTransform (), doft )
711
+ start_transform = numpy .eye (4 )
712
+ start_transform = cspec .ExtractTransform (start_transform , trajectory .GetWaypoint (0 ), robot )
713
+ traj_start = openravepy .RaveGetAffineDOFValuesFromTransform (start_transform , doft )
714
+
715
+ # Compare translation distance
716
+ trans_delta_value = abs (current_pose [:2 ] - traj_start [:2 ])
717
+ trans_resolution = robot .GetAffineTranslationResolution ()[:2 ]
718
+ if trans_delta_value [0 ] > trans_resolution [0 ] or \
719
+ trans_delta_value [1 ] > trans_resolution [1 ]:
713
720
return False
721
+
722
+ # Compare rotation distance
723
+ rot_delta_value = abs (wrap_to_interval (current_pose [2 ] - traj_start [2 ]))
724
+ rot_resolution = robot .GetAffineRotationAxisResolution ()[2 ] # Rotation about z?
725
+ if rot_delta_value > rot_resolution :
726
+ return False
727
+
728
+ else :
729
+ # Get used indices and starting configuration from trajectory.
730
+ dof_indices , _ = cspec .ExtractUsedIndices (robot )
731
+ traj_values = cspec .ExtractJointValues (
732
+ trajectory .GetWaypoint (0 ), robot , dof_indices )
733
+
734
+ # Get current configuration of robot for used indices.
735
+ with robot .GetEnv ():
736
+ robot_values = robot .GetDOFValues (dof_indices )
737
+ dof_resolutions = robot .GetDOFResolutions (dof_indices )
738
+
739
+ # Check deviation in each DOF, using OpenRAVE's SubtractValue function.
740
+ dof_infos = zip (dof_indices , traj_values , robot_values , dof_resolutions )
741
+ for dof_index , traj_value , robot_value , dof_resolution in dof_infos :
742
+ # Look up the Joint and Axis of the DOF from the robot.
743
+ joint = robot .GetJointFromDOFIndex (dof_index )
744
+ axis = dof_index - joint .GetDOFIndex ()
745
+
746
+ # If any joint deviates too much, return False.
747
+ delta_value = abs (joint .SubtractValue (traj_value , robot_value , axis ))
748
+ if delta_value > dof_resolution :
749
+ return False
714
750
715
751
# If all joints match, return True.
716
752
return True
@@ -1116,3 +1152,17 @@ def BodyPointsStateFromTraj(bodypoints, traj, time, derivatives=[0, 1, 2]):
1116
1152
"""
1117
1153
return BodyPointsStatesFromTraj (bodypoints , traj , (time ,), derivatives )[0 ]
1118
1154
1155
+ def wrap_to_interval (angles , lower = - numpy .pi ):
1156
+ """
1157
+ Wraps an angle into a semi-closed interval of width 2*pi.
1158
+ By default, this interval is `[-pi, pi)`. However, the lower bound of the
1159
+ interval can be specified to wrap to the interval `[lower, lower + 2*pi)`.
1160
+ If `lower` is an array the same length as angles, the bounds will be
1161
+ applied element-wise to each angle in `angles`.
1162
+ See: http://stackoverflow.com/a/32266181
1163
+ @param angles an angle or 1D array of angles to wrap
1164
+ @type angles float or numpy.array
1165
+ @param lower optional lower bound on wrapping interval
1166
+ @type lower float or numpy.array
1167
+ """
1168
+ return (angles - lower ) % (2 * numpy .pi ) + lower
0 commit comments