00001 import roslib
00002 roslib.load_manifest( 'rospy' )
00003 roslib.load_manifest( 'rosparam' )
00004 roslib.load_manifest( 'actionlib' )
00005 roslib.load_manifest( 'trajectory_msgs' )
00006 roslib.load_manifest( 'pr2_controllers_msgs' )
00007
00008 import rospy
00009 import rosparam
00010
00011 import csv
00012
00013 from actionlib import \
00014 SimpleActionClient
00015 from trajectory_msgs.msg import \
00016 JointTrajectory, JointTrajectoryPoint
00017 from pr2_controllers_msgs.msg import \
00018 JointTrajectoryAction, JointTrajectoryGoal
00019
00020 import numpy as np
00021 from math import fmod, pi
00022 import pickle
00023
00024
00025
00026
00027
00028 def wrap_angle( a ):
00029 if a < 0:
00030 return fmod( a - pi, 2 * pi ) + pi
00031 if a > 0:
00032 return fmod( a + pi, 2 * pi ) - pi
00033
00034 def wrap_trajectory( t ):
00035 rospy.loginfo( 'warapping trajectory [#points: %d] ...', len( t ) )
00036 b = 0.1
00037 if len( t ) < 0:
00038 return
00039 last = map( wrap_angle, t[0])
00040 offsets = np.zeros( len( last ) )
00041 for i in range( len( t ) ):
00042 for j in range( len( t[i] ) ):
00043 a = wrap_angle( t[i,j] )
00044
00045 if a > pi - b and last[j] < -pi + b:
00046 offsets[j] -= 2 * pi
00047 if a < -pi + b and last[j] > pi - b:
00048 offsets[j] += 2 * pi
00049
00050 last[j] = a
00051
00052 t[i] += offsets
00053 rospy.loginfo( 'done!' )
00054
00055 def compute_derivative( f, dt ):
00056 rospy.loginfo( 'computing derivative [#points: %d] ...', len( f ) )
00057 f_dot = np.zeros( f.shape )
00058 for i in range( 1, len( f ) - 1 ):
00059 for j in range( len( f[i] ) ):
00060 f_dot[i,j] = (f[i+1,j] - f[i-1,j]) / (2.0 * dt)
00061 f_dot[0,:] = (f[1,:] - f[-1,:]) / (2.0 * dt)
00062 f_dot[-1,:] = (f[0,:] - f[-2,:]) / (2.0 * dt)
00063 rospy.loginfo( 'done!' )
00064 return f_dot
00065
00066 def save_motion( fname, name, time, pos, vel, acc ):
00067 rospy.loginfo( 'save motion \'%s\' to file: %s'%( name, fname ) )
00068 pkl_file = open( fname, 'wb' )
00069 data = ( name, time, pos, vel, acc )
00070 pickle.dump( data, pkl_file )
00071 pkl_file.close()
00072 rospy.loginfo( 'done!' )
00073
00074 def load_motion( fname ):
00075 rospy.loginfo( 'loading motion from file: %s'%fname )
00076 pkl_file = open( fname, 'rb' )
00077 data = pickle.load( pkl_file )
00078 rospy.loginfo( 'done!' )
00079 return data
00080
00081 def load_motion_ascii( fname ):
00082 reader = csv.reader( open( fname, 'rb' ), delimiter="\t" )
00083 t = []
00084 pos = []
00085 vel = []
00086 acc = []
00087 for row in reader:
00088 t.append( float(row[0]) )
00089 pos.append( map( lambda x: float(x), row[1:8] ) )
00090 vel.append( map( lambda x: float(x), row[8:15] ) )
00091 acc.append( map( lambda x: float(x), row[15:22] ) )
00092 return (fname, np.asarray(t), np.asarray(pos), np.asarray(vel), np.asarray(acc))
00093
00094
00095
00096
00097
00098 def init_jt_client(arm = 'r'):
00099 name = "".join( [ arm, "_arm_controller/joint_trajectory_action" ] )
00100 client = SimpleActionClient(name, JointTrajectoryAction)
00101 rospy.loginfo( 'waiting for action client : %s ...'%name )
00102 client.wait_for_server()
00103 rospy.loginfo( '%s is up and running!'%name )
00104 return client
00105
00106 def get_joint_names( node_name ):
00107 return rosparam.get_param( ''.join( (node_name, '/joints') ) )
00108
00109 def move_arm( positions, time_from_start = 3.0, arm = 'r', client = None ):
00110
00111 if (client == None):
00112 client = init_jt_client(arm)
00113 else:
00114 arm = client.action_client.ns[0:1];
00115
00116 rospy.loginfo( 'move arm \'%s\' to position %s'%( arm, positions ) )
00117
00118 joint_names = get_joint_names( ''.join( ( arm, '_arm_controller' ) ) )
00119
00120 jt = JointTrajectory()
00121 jt.joint_names = joint_names
00122 jt.points = []
00123 jp = JointTrajectoryPoint()
00124 jp.time_from_start = rospy.Time.from_seconds( time_from_start )
00125 jp.positions = positions
00126 jt.points.append( jp )
00127
00128
00129 jt_goal = JointTrajectoryGoal()
00130 jt_goal.trajectory = jt
00131 jt_goal.trajectory.header.stamp = rospy.Time.now()
00132 client.send_goal( jt_goal )
00133 client.wait_for_result()
00134 return client.get_state()
00135
00136
00137 def track_trajectory( pos, vel, acc, time,
00138 arm = 'r', client = None,
00139 stamp = None):
00140
00141 if (acc == None):
00142 acc = np.zeros( pos.shape )
00143
00144 if ( len( pos ) != len( vel ) or len( pos ) != len( time ) ):
00145 rospy.logerr( '[track_trajectory] dimensions do not agree' )
00146
00147 rospy.loginfo( 'arm \'%s\' tracking trajectory with %d points'
00148 %( arm, len( pos ) ) )
00149
00150 if (client == None):
00151 client = init_jt_client(arm)
00152 else:
00153 arm = client.action_client.ns[0:1];
00154
00155 joint_names = get_joint_names( ''.join( ( arm, '_arm_controller' ) ) )
00156
00157
00158 jt = JointTrajectory()
00159 jt.joint_names = joint_names
00160 jt.points = []
00161
00162 t = 0
00163 for i in range( len( pos ) ):
00164 jp = JointTrajectoryPoint()
00165 jp.time_from_start = rospy.Time.from_sec( time[i] )
00166 jp.positions = pos[i,:]
00167 jp.velocities = vel[i,:]
00168 jp.accelerations = acc[i,:]
00169 jt.points.append( jp )
00170 t += 1
00171
00172 if ( stamp == None ):
00173 stamp = rospy.Time.now()
00174
00175
00176 jt_goal = JointTrajectoryGoal()
00177 jt_goal.trajectory = jt
00178 jt_goal.trajectory.header.stamp = stamp;
00179 client.send_goal(jt_goal)
00180