MAGIKS  1.1
Manipulator General Inverse Kinematic Solver
 All Classes Namespaces Files Functions Variables Pages
skilled_pr2.py
Go to the documentation of this file.
1 ## @file skilled_pr2.py
2 # @brief Contains a class inherited from PyRide_PR2 in pyride_synchronizer.py which is connected to a real-time robot,
3 # a real PR2 or PR2 in simulation that have special skills like drawing
4 # @author Nima Ramezani Taghiabadi
5 #
6 # PhD Researcher
7 # Faculty of Engineering and Information Technology
8 # University of Technology Sydney (UTS)
9 # Broadway, Ultimo, NSW 2007, Australia
10 # Phone No. : 04 5027 4611
11 # Email(1) : nima.ramezani@gmail.com
12 # Email(2) : Nima.RamezaniTaghiabadi@uts.edu.au
13 # @version 3.0
14 #
15 # Start date: 17 September 2014
16 # Last Revision: 06 January 2015
17 
18 import numpy as np
19 import time
20 import pyride_synchronizer
21 import pyride_interpreter as pint
22 
23 from math_tools import general_math as gen
24 from math_tools.geometry import trajectory as traj, rotation as rot
25 
26 '''
27 import sys
28 sys.path.append()
29 '''
30 
31 '''
32 writing posture:
33 array([ -1.26299826e-01, 1.77046412e+00, -1.02862191e+00,
34  -1.36864905e+00, -2.31195189e+00, -1.29253137e+00,
35  1.71195615e-01, 8.02176174e-01, -2.12167293e-03,
36  2.32811863e-04, 7.05358701e-03, 4.01010384e-01,
37  2.44565260e+00, 7.10476515e-01, -1.30808585e+00,
38  1.15357810e+00, -4.49485156e-01, -2.46943329e+00])
39 '''
41  def __init__(self, run_magiks = False):
42  super(Skilled_PR2, self).__init__(run_magiks = run_magiks)
43  self.height = 0.05
44  self.width = 0.05
45  self.depth = 0.02
46  self.write_from_shape = True
48  self.timeout = 20.0
49  self.arm_speed = 0.05
50 
51  self.larm_startpoint = None
52  self.rarm_startpoint = None
53  self.larm_endpoint_width = None
54  self.rarm_endpoint_width = None
57 
58  d = 0.5
59  self.rarm_startpoint = np.array([ d-0.05, - 0.1, 0.0])
60  self.larm_startpoint = np.array([ d-0.05, + 0.4, 0.0])
61  self.rarm_endpoint_width = np.array([ d-0.05, - 0.4, 0.0])
62  self.larm_endpoint_width = np.array([ d-0.05, + 0.1, 0.0])
63  self.rarm_endpoint_height = np.array([ d-0.05, - 0.1, 0.2])
64  self.larm_endpoint_height = np.array([ d-0.05, + 0.4, 0.2])
65 
66  self.board_offset = np.array([0.1, 0.2, 0.05])
67 
68  self.box_width_rarm = 0.3
69  self.box_height_rarm = 0.2
70  self.box_width_larm = 0.3
71  self.box_height_larm = 0.2
72 
73  def keep_reference(self, q = None):
74  '''
75  Sets the configuration given by q as the reference configuration
76  If q is not given, it reads the robot arm joints and sets them as reference configuration
77  '''
78  if q == None:
79  self.ref_config = np.copy(self.q)
80  else:
81  keep_config = np.copy(self.q)
82  assert self.set_config(q), "Error from Skilled_PR2.set_reference(): Given joints are not feasible"
83  self.ref_config = self.q
84  self.q = np.copy(keep_config)
85 
86  def set_reference_arms(self, ttr = 2.5):
87  if self.set_config(self.ref_config):
88  qr = self.rarm.config.q
89  ql = self.larm.config.q
90  pint.take_rarm_to(qr, time_to_reach = ttr)
91  pint.take_larm_to(ql, time_to_reach = ttr)
92  self.sync_object()
93  else:
94  assert False, "This should not happen"
95 
96  def catch_the_board(self):
97  # self.switch_arm()
98  qr = np.array([ 0.08842831, 2.34773988, 0.07718497, -1.32087472, -0.71994221, -1.02121596, -1.56155048])
99  self.rarm.set_config(qr)
100  self.sync_robot()
101  pint.set_rg(2)
102  self.say("Please, put the bord in my right hand")
103  time.sleep(10)
104  pint.set_rg(0)
105  self.say("Thank you")
106 
107  def catch_the_pen(self):
108  # self.switch_arm()
109  pint.set_lg(2)
110  self.say("Please, put the pen in my left hand")
111  time.sleep(5)
112  pint.set_lg(1)
113  self.say("Thank you")
114 
115  def prepare_to_write(self):
116  self.say("Let's draw something. Show me a board")
117  self.sync_object()
118  pint.activate_tilt_laser()
119  while pint.tl_dist == None:
120  time.sleep(0.01)
121 
122  N = len(pint.tl_dist)/2
123  d = pint.tl_dist[N]
124  while d > 1.0:
125  d = pint.tl_dist[N]
126 
127  self.catch_the_board()
128  time.sleep(3)
129  self.catch_the_pen()
130  time.sleep(5)
131  # self.get_ready(False)
132  pint.deactivate_tilt_laser()
133 
134  def show_the_people(self, return_back = True):
135  ql = np.array([ 1.1742804 , 2.04188103, 1.35847037, -1.99603627, -1.22890376, -1.16233047, 0.80086808])
136  self.larm.set_config(ql)
137  self.sync_robot()
138  qr = np.array([-0.37128888, 2.08050452, -1.08169936, -1.27411378, 0.92031194, -1.3185062 , 1.23221083])
139  self.rarm.set_config(qr)
140  self.sync_robot()
141 
142  self.say("How was it?")
143  if return_back:
144  time.sleep(5)
145  qr = np.array([ 0.08842831, 2.34773988, 0.07718497, -1.32087472, -0.71994221, -1.02121596, -1.56155048])
146  self.rarm.set_config(qr)
147  self.sync_robot()
148  self.larm_reference = True
149  self.get_ready(False)
150 
152  self.sync_object()
153  if self.larm_reference:
154  self.larm_startpoint = np.copy(self.larm.wrist_position())
155  else:
156  self.rarm_startpoint = np.copy(self.rarm.wrist_position())
157 
158  def calibrate_width(self):
159  self.sync_object()
160  if self.larm_reference:
161  self.larm_endpoint_width = np.copy(self.larm.wrist_position())
162  else:
163  self.rarm_endpoint_width = np.copy(self.rarm.wrist_position())
164 
165  def calibrate_height(self):
166  self.sync_object()
167  if self.larm_reference:
168  self.larm_endpoint_height = np.copy(self.larm.wrist_position())
169  else:
170  self.rarm_endpoint_height = np.copy(self.rarm.wrist_position())
171 
172  def get_ready(self, only_orientation = True, reverse = False):
173  self.sync_object()
174  if self.larm_reference:
175  ori = self.rarm.wrist_orientation()
176  pos = self.rarm_end_position()
177  else:
178  ori = self.larm.wrist_orientation()
179  pos = self.larm_end_position()
180 
181  if reverse:
182  ori = rot.reverse(ori)
183  R = rot.orthogonal(ori)
184 
185  if only_orientation:
186  arm = self.reference_arm()
187  p = arm.wrist_position()
188  arm.set_target(p, R)
189  self.arm_target()
190  else:
191  n = R[:,2]
192  h = R[:,1]
193  w = R[:,0]
194 
195  p = pos - (self.board_offset[0]+self.depth)*n + self.board_offset[2]*h + self.board_offset[1]*w
196 
197  self.set_target(p, R)
198  self.goto_target()
199  self.sync_robot()
200 
201  if self.larm_reference:
202  pint.look_lg()
203  else:
204  pint.look_rg()
205 
206  self.calibrate_startpoint()
207 
208  def writing_posture(self):
209  if self.larm_startpoint == None:
210  print "Left Arm is not calibrated!"
211  else:
212  pos = self.larm_startpoint
213  if (self.larm_endpoint_width == None) or (self.larm_endpoint_height == None):
214  ori = ps.rot.point_forward_orientation
215  else:
216  z = self.larm_endpoint_height - self.larm_startpoint
217  self.box_height_larm = np.linalg.norm(z)
218  z = z/self.box_height_larm
219  y = self.larm_endpoint_width - self.larm_startpoint
220  if y[1] < 0:
221  y = y/self.box_width_larm
222  else:
223  y = - y/self.box_width_larm
224  self.box_width_larm = np.linalg.norm(y)
225  y = - y/self.box_width_larm
226  x = np.cross(y, z)
227  x = x/np.linalg.norm(x)
228  # Correct z:
229  z = np.cross(x, y)
230  ori = np.append(np.append([y],[z],axis = 0), [x], axis = 0).T
231  assert gen.equal(np.linalg.det(ori), 1.0)
232  n = ori[:,2]
233  self.larm.set_target(pos - self.depth*n, ori)
234 
235  if self.rarm_startpoint == None:
236  print "Right Arm is not calibrated!"
237  else:
238  pos = self.rarm_startpoint
239  if (self.rarm_endpoint_width == None) or (self.rarm_endpoint_height == None):
240  ori = ps.rot.point_forward_orientation
241  else:
242  z = self.rarm_endpoint_height - self.rarm_startpoint
243  self.box_height_rarm = np.linalg.norm(z)
244  z = z/self.box_height_rarm
245  y = self.rarm_endpoint_width - self.rarm_startpoint
246  self.box_width_rarm = np.linalg.norm(y)
247  if y[1] < 0:
248  y = - y/self.box_width_rarm
249  else:
250  y = y/self.box_width_rarm
251  x = np.cross(y, z)
252  x = x/np.linalg.norm(x)
253  # Correct z:
254  z = np.cross(x, y)
255  ori = np.append(np.append([y],[z],axis = 0), [x], axis = 0).T
256  assert gen.equal(np.linalg.det(ori), 1.0)
257  n = ori[:,2]
258  self.rarm.set_target(pos-self.depth*n, ori)
259 
260  self.larm_target(wait = False)
261  self.rarm_target(wait = False)
262  pint.wait_until_finished(target_list = ['rarm', 'larm'])
263  self.sync_object()
264  '''
265  '''
266 
267  def draw_shape(self, shape_trajectory):# add wait argument later
268  arm = self.reference_arm()
269  keep_dt = arm.dt
270  arm.dt = shape_trajectory.phi_end/100
271  jt = arm.js_project(shape_trajectory, relative = False, traj_type = 'polynomial')
272  arm.dt = keep_dt
273  # jt.fix_points()
274  jt.consistent_velocities()
275  # jt.plot()
276  if not gen.equal(jt.phi_end, shape_trajectory.phi_end):
277  print "Warning from PyRide_PR2.draw_shape(): All the shape is not in the workspace. Part of it will be drawn !"
278 
279  L = sum(shape_trajectory.points_dist())
280  '''
281  shape_trajectory.plot3d()
282  for j in range(7):
283  jt.plot(axis = j, show_points = True)
284  '''
285  pint.run_config_trajectory(jt, duration = L/self.arm_speed, is_left_arm = self.larm_reference)
286 
287  def switch_arm(self):
288  if self.larm_reference:
289  self.larm_reference = False
290  else:
291  self.larm_reference = True
292 
293  def draw_from_canvas(self, canvas_shapes, width_pixels = 640, height_pixels = 480, plot = False, silent=True):
294  self.sync_object()
295 
296  ori_l = self.larm.wrist_orientation()
297  ori_r = self.rarm.wrist_orientation()
298  wr = - ori_r[:,0]
299  hr = ori_r[:,1]
300  nr = ori_r[:,2]
301  wl = - ori_l[:,0]
302  hl = ori_l[:,1]
303  nl = ori_l[:,2]
304 
305  self.control_mode = "Fixed-Base"
306  self.larm_reference = False
307 
308  self.rarm_startpoint = self.rarm_startpoint + nr*self.depth
309  self.larm_startpoint = self.larm_startpoint + nl*self.depth
310 
311  pr_list = []
312  pl_list = []
313 
314  for cs in canvas_shapes:
315  if cs.arm == "R":
316  phi = 1.0
317  (x0,y0) = cs.pts[0]
318  pos0 = self.rarm_startpoint + self.box_width_rarm*x0*wr/width_pixels + self.box_height_rarm*(height_pixels-y0)*hr/height_pixels
319  pr = traj.Trajectory_Polynomial(dimension = 3)
320  pr.add_point(0.0, np.copy(pos0), np.zeros(3))
321  for (x,y) in cs.pts[1:]:
322  pos = self.rarm_startpoint + self.box_width_rarm*x*wr/width_pixels + self.box_height_rarm*(height_pixels-y)*hr/height_pixels
323  pr.add_point(phi, pos)
324  # pr.new_segment()
325  phi += 1.0
326 
327  pr.consistent_velocities()
328  pr_list.append(pr)
329  if plot:
330  pr.plot3d()
331  elif cs.arm == "L":
332  phi = 1.0
333  (x0,y0) = cs.pts[0]
334  pos0 = self.larm_startpoint + self.box_width_larm*x0*wl/width_pixels + self.box_height_larm*(height_pixels-y0)*hl/height_pixels
335  pl = traj.Trajectory_Polynomial(dimension = 3)
336  pl.add_point(0.0, np.copy(pos0), np.zeros(3))
337  for (x,y) in cs.pts[1:]:
338  pos = self.larm_startpoint + self.box_width_larm*x*wl/width_pixels + self.box_height_larm*(height_pixels-y)*hl/height_pixels
339  pl.add_point(phi, pos)
340  # pl.new_segment()
341  phi += 1.0
342 
343  pl.consistent_velocities()
344  pl_list.append(pl)
345  if plot:
346  pr.plot3d()
347  else:
348  assert False
349 
350 
351  ir = 0
352  il = 0
353  nrt = len(pr_list)
354  nlt = len(pl_list)
355  step_r = 0
356  step_l = 0
357  t0 = time.time()
358 
359  t = 0.0
360  # while ((ir < nrt) or (il < nlt)) and (not pint.rarm_failed) and (not pint.larm_failed) and (t < self.timeout):
361  while ((ir < nrt) or (il < nlt)) and (not pint.rarm_failed) and (not pint.larm_failed):
362 
363  # initial positioning:
364  if (ir < nrt) and (step_r == 0):
365  t0 = time.time()
366  if not silent:
367  print "Trajectory: ", ir, " Step 0 for Right Arm"
368  pr = pr_list[ir]
369  pos = np.copy(pr.segment[0].point[0].pos)
370  pos = pos - self.depth*nr
371  self.rarm.set_target(pos, ori_r)
372  assert self.rarm.goto_target(optimize = True)
373  pint.take_rarm_to(self.rarm.config.q, time_to_reach = 2.0)
374  step_r += 1
375 
376  if (il < nlt) and (step_l == 0):
377  t0 = time.time()
378  if not silent:
379  print "Trajectory: ", il, " Step 0 for Left Arm"
380  pl = pl_list[il]
381  pos = np.copy(pl.segment[0].point[0].pos)
382  pos = pos - self.depth*nl
383  self.larm.set_target(pos, ori_l)
384  assert self.larm.goto_target(optimize = True)
385  pint.take_larm_to(self.larm.config.q, time_to_reach = 2.0)
386  step_l += 1
387  # head forward:
388  if (pint.rarm_reached) and (step_r == 1):
389  t0 = time.time()
390  if not silent:
391  print "Trajectory: ", ir, " Step 1 for Right Arm"
392  pos = np.copy(pr.segment[0].point[0].pos)
393  self.rarm.set_target(pos, ori_r)
394  assert self.rarm.goto_target(optimize = True)
395  pint.take_rarm_to(self.rarm.config.q, time_to_reach = 1.0)
396  step_r += 1
397 
398  if (pint.larm_reached) and (step_l == 1):
399  t0 = time.time()
400  if not silent:
401  print "Trajectory: ", il, " Step 1 for Left Arm"
402  pos = np.copy(pl.segment[0].point[0].pos)
403  self.larm.set_target(pos, ori_l)
404  assert self.larm.goto_target(optimize = True)
405  pint.take_larm_to(self.larm.config.q, time_to_reach = 1.0)
406  step_l += 1
407 
408  # run trajectory:
409  if (pint.rarm_reached) and (step_r == 2):
410  t0 = time.time()
411  if not silent:
412  print "Trajectory: ", ir, " Step 2 for Right Arm"
413  self.larm_reference = False
414  # self.arm_trajectory(pr, relative = False, delta_phi = 0.5, wait = False)
415  self.draw_shape(pr)
416  step_r += 1
417 
418  if (pint.larm_reached) and (step_l == 2):
419  t0 = time.time()
420  if not silent:
421  print "Trajectory: ", il, " Step 2 for Left Arm"
422  self.larm_reference = True
423  # self.arm_trajectory(pl, relative = False, delta_phi = 0.5, wait = False)
424  nseg = len(pl.segment)
425  # print "len(pl.segment)", nseg
426  # print "num.points.last.seg:", len(pl.segment[nseg-1].point)
427  #print pl.segment[nseg-1].point[0]
428  #print pl.segment[nseg-1].point[1]
429  #print pl.segment[nseg-1].points_dist()
430 
431  self.draw_shape(pl)
432  step_l += 1
433 
434  # head backward:
435  if (pint.rarm_reached) and (step_r == 3):
436  t0 = time.time()
437  if not silent:
438  print "Trajectory: ", ir, " Step 3 for Right Arm"
439 
440  self.sync_object()
441  pos = self.rarm.wrist_position() - nr*self.depth
442  self.rarm.set_target(pos, ori_r)
443  assert self.rarm.goto_target(optimize = True)
444  pint.take_rarm_to(self.rarm.config.q, time_to_reach = 1.0)
445  step_r += 1
446 
447  if (pint.larm_reached) and (step_l == 3):
448  t0 = time.time()
449  if not silent:
450  print "Trajectory: ", il, " Step 3 for Left Arm"
451 
452  self.sync_object()
453  pos = self.larm.wrist_position() - nl*self.depth
454  self.larm.set_target(pos, ori_l)
455  assert self.larm.goto_target(optimize = True)
456  pint.take_larm_to(self.larm.config.q, time_to_reach = 1.0)
457  '''
458  self.larm_reference = True
459  self.arm_back(dx = self.depth, relative = True)
460  '''
461  step_l += 1
462 
463  if (pint.rarm_reached) and (step_r == 4):
464  t0 = time.time()
465  if not silent:
466  print "Trajectory: ", ir, " Step 4 for Right Arm"
467  ir += 1
468  step_r = 0
469 
470  if (pint.larm_reached) and (step_l == 4):
471  t0 = time.time()
472  if not silent:
473  print "Trajectory: ", il, " Step 4 for Left Arm"
474  il += 1
475  step_l = 0
476 
477  time.sleep(0.100)
478  t = time.time() - t0
479 
480  self.sync_object()
481  self.rarm_startpoint = self.rarm_startpoint - nr*self.depth
482  self.larm_startpoint = self.larm_startpoint - nl*self.depth
483 
484  if t > self.timeout:
485  print "Action not completed! Time Out!"
486  # Return back to start point:
487  if nrt > 0:
488  self.rarm.set_target(self.rarm_startpoint, ori_r)
489  self.rarm_target(wait = True)
490 
491  if nlt > 0:
492  self.larm.set_target(self.larm_startpoint, ori_l)
493  self.larm_target(wait = True)
494 
495 
def sync_robot
Synchronizes the real robot or robot in simulation with the object.
def sync_object
Synchronizes the object with the robot and verifies the equity of forward kinematics for both the rig...
def larm_target
Solves the Inverse Kinematics for the left arm with given redundant parameter and takes the right ar...
This class introduces a data structure for complete kinematics of a PR2 robot which can sychronize it...
def say
Use this function if you want the robot to say something.
def arm_target
Solves the Inverse Kinematics for the reference arm with given redundant parameter The instructions ...
arm_speed
A float specifying the speed of arm gripper in the operational space in m/sec.
def rarm_target
Solves the Inverse Kinematics for the right arm with given redundant parameter and takes the right a...