sm_cleaning_learning.py
Go to the documentation of this file.
00001 #!/usr/bin/env python
00002 # -*- coding: utf-8 -*-
00003 
00004 import roslib; roslib.load_manifest('iri_clean_board')
00005 import rospy
00006 import smach
00007 import smach_ros
00008 
00009 from smach_ros import SimpleActionState
00010 from smach_ros import ServiceState
00011 
00012 from actionlib import *
00013 from actionlib.msg import *
00014 
00015 from iri_common_smach import st_sleep
00016 
00017 from iri_clean_board.srv import *
00018 from estirabot_msgs.msg import *
00019 from estirabot_msgs.srv import *
00020 from iri_planning_msgs.srv import *
00021 
00022 class NeedInfo(smach.State):
00023         def __init__(self):
00024                 smach.State.__init__(self, outcomes=['next','failed'])
00025                 self.counter = 0
00026 
00027         def execute(self, userdata):
00028                 rospy.logdebug('Executing state NeedInfo')
00029                 return 'next'
00030 
00031 
00032 class GetInfoCamera(smach.State):
00033         def __init__(self):
00034                 smach.State.__init__(self, outcomes=['succeeded','preempted','aborted'],
00035                                      input_keys=[],
00036                                      output_keys=['segmented_image', 'pointcloud', 'plane_coefficients'])
00037                 self.service_topic = '/iri_clean_perception/get_board_information/get_board_info_srv'
00038         
00039         def execute(self, userdata):
00040                 rospy.logdebug('Executing state GetInfoCamera')
00041                 start_timer = time.time()
00042                 
00043                 rospy.wait_for_service(self.service_topic)
00044                 try:
00045                         get_service = rospy.ServiceProxy(self.service_topic, BoardInfo)
00046                         resp = get_service()
00047                         
00048                         userdata.segmented_image = resp.segmented_image
00049                         userdata.pointcloud = resp.pointcloud
00050                         userdata.plane_coefficients = resp.plane_coefficients
00051                         
00052                         stop_timer = time.time()
00053                         global time_perception
00054                         time_perception = time_perception + (stop_timer - start_timer)
00055                         return 'succeeded'
00056                 
00057                 except rospy.ServiceException, e:
00058                         print "Service call failed: %s"%e
00059                         return 'aborted'
00060 
00061 
00062 class PradaPlanning(smach.State):
00063         def __init__(self):
00064                 smach.State.__init__(self, outcomes=['succeeded','preempted','aborted','no_plan'],
00065                                      input_keys=['rules_updated_sm'],
00066                                      output_keys=['target_ellipses','actions'])
00067                 self.service_topic = '/iri_clean_plan/prada_planner/getBestAction'
00068         
00069         def execute(self, userdata):
00070                 rospy.logdebug('Executing state PradaPlanning')
00071                 
00072                 start_timer = time.time()
00073                 rospy.wait_for_service(self.service_topic)
00074                 try:
00075                         get_cleaning_plan = rospy.ServiceProxy(self.service_topic, PradaPlanSrv)
00076                         resp = get_cleaning_plan(userdata.rules_updated_sm)
00077                         
00078                         stop_timer = time.time()
00079                         global time_planning
00080                         time_planning = time_planning + (stop_timer - start_timer)
00081                         
00082                         if resp.succeeded:
00083                                 userdata.target_ellipses = resp.target_ellipses
00084                                 userdata.actions = resp.actions
00085                                 return 'succeeded'
00086                         else:
00087                                 return 'no_plan'
00088                 
00089                 except rospy.ServiceException, e:
00090                         print "Service call failed: %s"%e
00091                         return 'aborted'
00092 
00093 
00094 class CalculateTrajectories(smach.State):
00095         def __init__(self):
00096                 smach.State.__init__(self, outcomes=['succeeded','preempted','aborted','no_movements'],
00097                                      input_keys=['target_ellipses_sm','actions_sm','ellipses_sm','segmented_pointcloud_sm','plane_coefficients_sm'],
00098                                      output_keys=['poses','poses_2d_coordinates','secondary_arm'])
00099                 self.service_topic = '/iri_clean_plan/cleaning_plan/get_trajectories_from_plan'
00100         
00101         def execute(self, userdata):
00102                 rospy.logdebug('Executing state CalculateTrajectories')
00103                 start_timer = time.time()
00104                 rospy.wait_for_service(self.service_topic)
00105                 try:
00106                         get_cleaning_plan = rospy.ServiceProxy(self.service_topic, PlanToTrajectories)
00107                         resp = get_cleaning_plan(userdata.segmented_pointcloud_sm, userdata.plane_coefficients_sm, userdata.target_ellipses_sm, userdata.actions_sm)
00108                         
00109                         stop_timer = time.time()
00110                         global time_state
00111                         time_state = time_state + (stop_timer - start_timer)
00112                         
00113                         if resp.movement:
00114                                 userdata.poses = resp.poses
00115                                 userdata.poses_2d_coordinates = resp.poses_2d_coordinates
00116                                 userdata.secondary_arm = resp.secondary_arm
00117                                 return 'succeeded'
00118                         else:
00119                                 return 'no_movements'
00120                 
00121                 except rospy.ServiceException, e:
00122                         print "Service call failed: %s"%e
00123                         return 'aborted'
00124 
00125 
00126 class GetStateRepresentation(smach.State):
00127         def __init__(self):
00128                 smach.State.__init__(self, outcomes=['succeeded','preempted','aborted','is_clean','get_full_info'],
00129                                      input_keys=['segmented_image_sm','segmented_pointcloud_sm','plane_coefficients_sm'],
00130                                      output_keys=['dirty_areas','distances','state_string','arm_position','segmented_pointcloud_sm','plane_coefficients_sm'])
00131                 self.service_topic = '/iri_clean_plan/cleaning_plan/get_dirty_areas_state_representation'
00132                 self.surface_clean_perceptions = 0
00133         
00134         def execute(self, userdata):
00135                 rospy.logdebug('Executing state GetStateRepresentation')
00136                 start_timer = time.time()
00137                 rospy.wait_for_service(self.service_topic)
00138                 try:
00139                         get_state = rospy.ServiceProxy(self.service_topic, StateRepresentation)
00140                         resp = get_state(userdata.segmented_image_sm)
00141                         
00142                         stop_timer = time.time()
00143                         global time_state
00144                         time_state = time_state + (stop_timer - start_timer)
00145                         
00146                         if resp.is_clean:
00147                                 if self.surface_clean_perceptions < 2:
00148                                         self.surface_clean_perceptions += 1
00149                                         return 'get_full_info'
00150                                 else:
00151                                         return 'is_clean'
00152                         else:
00153                                 self.surface_clean_perceptions = 0
00154                                 userdata.dirty_areas = resp.dirty_areas
00155                                 userdata.distances = resp.distances
00156                                 userdata.arm_position = resp.arm_position
00157                                 userdata.state_string = resp.state_string
00158                                 return 'succeeded'
00159                 except rospy.ServiceException, e:
00160                         print "Service call failed: %s"%e
00161                         return 'aborted'
00162 
00163 
00164 class LearnerAddAction(smach.State):
00165         def __init__(self):
00166                 smach.State.__init__(self, outcomes=['needs_learning','succeeded','preempted','aborted'],
00167                                      input_keys=['target_ellipses_sm','actions_sm','dirty_areas_sm','distances_sm','state_string_sm','movements_ok_sm'],
00168                                      output_keys=[])
00169                 self.service_topic = '/iri_learning/rule_learner/add_action'
00170         
00171         def execute(self, userdata):
00172                 rospy.logdebug('Executing state LearnerAddAction')
00173                 start_timer = time.time()
00174                 rospy.wait_for_service(self.service_topic)
00175                 try:
00176                         get_cleaning_plan = rospy.ServiceProxy(self.service_topic, AddAction)
00177                         resp = get_cleaning_plan(userdata.actions_sm[0], userdata.dirty_areas_sm, userdata.target_ellipses_sm[0], userdata.distances_sm, userdata.state_string_sm, userdata.movements_ok_sm)
00178                         
00179                         stop_timer = time.time()
00180                         global time_learning
00181                         time_learning = time_learning + (stop_timer - start_timer)
00182                         
00183                         if resp.needs_learning:
00184                                 return 'needs_learning'
00185                         else:
00186                                 return 'succeeded'
00187                 
00188                 except rospy.ServiceException, e:
00189                         print "Service call failed: %s"%e
00190                         return 'aborted'
00191 
00192 
00193 class LearnerAddState(smach.State):
00194         def __init__(self):
00195                 smach.State.__init__(self, outcomes=['succeeded','preempted','aborted'],
00196                                      input_keys=['segmented_image_sm'],
00197                                      output_keys=['rules_updated'])
00198                 self.service_topic = '/iri_learning/rule_learner/add_state'
00199         
00200         def execute(self, userdata):
00201                 rospy.logdebug('Executing state LearnerAddState')
00202                 start_timer = time.time()
00203                 rospy.wait_for_service(self.service_topic)
00204                 try:
00205                         get_cleaning_plan = rospy.ServiceProxy(self.service_topic, AddState)
00206                         resp = get_cleaning_plan(userdata.segmented_image_sm)
00207                         
00208                         stop_timer = time.time()
00209                         global time_learning
00210                         time_learning = time_learning + (stop_timer - start_timer)
00211                         
00212                         userdata.rules_updated = resp.rules_updated
00213                         return 'succeeded'
00214                 
00215                 except rospy.ServiceException, e:
00216                         print "Service call failed: %s"%e
00217                         return 'aborted'
00218 
00219 
00220 class MoveArm(smach.State):
00221         def __init__(self):
00222                 smach.State.__init__(self, outcomes=['succeeded','failed'],
00223                                         input_keys=['poses','plane_coefficients_sm','poses_2d_coordinates','secondary_arm'],
00224                                         output_keys=['movements_ok'])
00225 
00226         def execute(self, userdata):
00227                 rospy.logdebug('Waiting for service')
00228                 start_timer = time.time()
00229                 rospy.wait_for_service('/iri_clean_plan/arm_movements_by_pose/clean_movement')
00230                 try:
00231                         move_arm = rospy.ServiceProxy('/iri_clean_plan/arm_movements_by_pose/clean_movement', ArmMovementsPosesSrv)
00232                         resp = move_arm(userdata.poses, userdata.secondary_arm, userdata.plane_coefficients_sm, 1)
00233                         
00234                         stop_timer = time.time()
00235                         global time_moving
00236                         time_moving = time_moving + (stop_timer - start_timer)
00237                         
00238                         if resp.success:
00239                                 print 'Executing service success'
00240                                 userdata.movements_ok = True
00241                                 return 'succeeded'
00242                         else:
00243                                 # publish unreachable points
00244                                 pub = rospy.Publisher('/iri_clean_perception/get_board_information/unreachable_position', ImagePoint)
00245                                 for idx in resp.too_far_points_indexes:
00246                                         pub.publish(userdata.poses_2d_coordinates[idx])
00247                                 print 'Executing service failed. Maybe IK.'
00248                                 userdata.movements_ok = False
00249                                 return 'succeeded'
00250                 except rospy.ServiceException, e:
00251                         print "Service call failed: %s"%e
00252                         return 'failed'
00253 
00254 
00255 class MoveArmBase(smach.State):
00256         def __init__(self):
00257                 smach.State.__init__(self, outcomes=['next','failed'])
00258 
00259         def execute(self, userdata):
00260                 rospy.loginfo('Waiting for service')
00261                 start_timer = time.time()
00262                 rospy.wait_for_service('/iri_clean_plan/arm_movements_by_pose/clean_movement')
00263                 try:
00264                         # make a empty service message
00265                         clean_mov = ArmMovementsPosesSrv()
00266                         clean_mov.movement_type = 0
00267                         clean_mov.poses = [];
00268                         move_arm = rospy.ServiceProxy('/iri_clean_plan/arm_movements_by_pose/clean_movement', ArmMovementsPosesSrv)
00269                         resp = move_arm(clean_mov.poses, [], [], 0)
00270                         
00271                         stop_timer = time.time()
00272                         global time_moving
00273                         time_moving = time_moving + (stop_timer - start_timer)
00274                         
00275                         if resp.success:
00276                                 print 'Executing service success'
00277                                 return 'next'
00278                         else:
00279                                 print 'Executing service  failed'
00280                                 return 'next'
00281                 except rospy.ServiceException, e:
00282                         print "Service call failed: %s"%e
00283                         return 'failed'
00284 
00285 
00286 class MoveArmBaseWait(smach.State):
00287         def __init__(self):
00288                 smach.State.__init__(self, outcomes=['next','failed'])
00289 
00290         def execute(self, userdata):
00291                 rospy.loginfo('Waiting for service')
00292                 start_timer = time.time()
00293                 rospy.wait_for_service('/iri_clean_plan/arm_movements_by_pose/clean_movement')
00294                 try:
00295                         # make a empty service message
00296                         clean_mov = ArmMovementsPosesSrv()
00297                         clean_mov.movement_type = 0
00298                         clean_mov.poses = [];
00299                         move_arm = rospy.ServiceProxy('/iri_clean_plan/arm_movements_by_pose/clean_movement', ArmMovementsPosesSrv)
00300                         resp = move_arm(clean_mov.poses, [], [], 0)
00301                         
00302                         stop_timer = time.time()
00303                         global time_extra_learn
00304                         time_extra_learn = time_extra_learn + (stop_timer - start_timer) + 1.0
00305                         
00306                         if resp.success:
00307                                 print 'Executing service success'
00308                                 return 'next'
00309                         else:
00310                                 print 'Executing service  failed'
00311                                 return 'next'
00312                 except rospy.ServiceException, e:
00313                         print "Service call failed: %s"%e
00314                         return 'failed'
00315 
00316 
00317 def calculate_trajectories_cb(userdata, request):
00318         #traj_request = PlanToTrajectories().Request
00319         request.pointcloud_in = userdata.segmented_pointcloud_sm
00320         request.plane_coefficients = userdata.plane_coefficients_sm
00321         request.target_ellipses = userdata.target_ellipses_sm
00322         request.actions = userdata.actions_sm
00323         return request
00324 
00325 
00326 def main():
00327         rospy.init_node('smach_example_state_machine')
00328 
00329         # Create a SMACH state machine
00330         sm = smach.StateMachine(outcomes=['finishOk','failedVision','failedPlanning','failedMoveArm'])
00331         
00332         # Open the container
00333         with sm:
00334                 # Add states to the container
00335                 smach.StateMachine.add('NeedInfo', NeedInfo(),
00336                                 transitions={'next':'GetInfoCamera', 
00337                                                 'failed':'failedVision'},)
00338                                                 
00339                 smach.StateMachine.add('GetInfoCamera', GetInfoCamera(),
00340                                 #ServiceState('/iri_clean_perception/get_board_information/get_board_info_srv',
00341                                                         #BoardInfo,
00342                                                         #response_slots=['segmented_image', 
00343                                                                         #'pointcloud',
00344                                                                         #'plane_coefficients']),
00345                                 transitions={'succeeded':'LearnerAddState',
00346                                                 'preempted':'failedVision',
00347                                                 'aborted':'failedVision'},
00348                                 remapping={'segmented_image':'segmented_image_sm',
00349                                                 'pointcloud':'segmented_pointcloud_sm',
00350                                                 'plane_coefficients':'plane_coefficients_sm'})
00351                 
00352                 smach.StateMachine.add('LearnerAddState', LearnerAddState(),
00353                                 transitions={'succeeded':'GetStateRepresentation',
00354                                                 'preempted':'failedPlanning',
00355                                                 'aborted':'failedPlanning'},
00356                                 remapping={'rules_updated':'rules_updated_sm'})
00357                 
00358                 
00359                 smach.StateMachine.add('GetStateRepresentation',
00360                                 GetStateRepresentation(),
00361                                 transitions={'is_clean':'finishOk',
00362                                                 'get_full_info':'MoveArmBase',
00363                                                 'succeeded':'PradaPlanning',
00364                                                 'preempted':'failedVision',
00365                                                 'aborted':'failedVision'},
00366                                 remapping={'dirty_areas':'dirty_areas_sm',
00367                                            'distances':'distances_sm',
00368                                            'state_string':'state_string_sm'})
00369                 
00370                 smach.StateMachine.add('PradaPlanning',
00371                                 #ServiceState('/iri_clean_plan/prada_planner/getBestAction',
00372                                                 #PradaPlanSrv,
00373                                                 #input_keys=['segmented_pointcloud_sm'],
00374                                                 #output_keys=['segmented_pointcloud_sm'],
00375                                                 #request_slots=['distances','max_widths','min_widths','sparse','num_objects','arm_position'],
00376                                                 #response_slots=['succeeded','target_ellipses','actions']),
00377                                 PradaPlanning(),
00378                                 transitions={'succeeded':'CalculateTrajectories',
00379                                                 'preempted':'failedPlanning',
00380                                                 'aborted':'failedPlanning',
00381                                                 'no_plan':'NeedInfo'},
00382                                 remapping={'target_ellipses':'target_ellipses_sm',
00383                                            'actions':'actions_sm'})
00384                 
00385                 
00386                 
00387                 smach.StateMachine.add('CalculateTrajectories', 
00388                                 CalculateTrajectories(),
00389                                 #ServiceState('/iri_clean_plan/cleaning_plan/get_trajectories_from_plan',
00390                                                 #PlanToTrajectories,
00391                                                 ##request_slots=['segmented_pointcloud_sm','plane_coefficients_sm','target_ellipses_sm','actions_sm'],
00392                                                 #request_cb = calculate_trajectories_cb,
00393                                                 #input_keys=['segmented_pointcloud_sm','plane_coefficients_sm','target_ellipses_sm','actions_sm']),
00394                                                 ##response_slots=['poses','plane_coefficients','poses_2d_coordinates','secondary_arm']),
00395                                 transitions={'succeeded':'MoveArm',
00396                                                 'preempted':'failedVision',
00397                                                 'aborted':'failedVision',
00398                                                 'no_movements':'NeedInfo'})
00399                 
00400                 
00401                 smach.StateMachine.add('MoveArm', MoveArm(), 
00402                                 transitions={'succeeded':'LearnerAddAction',
00403                                                 'failed':'failedMoveArm'},
00404                                 remapping={'movements_ok':'movements_ok_sm'})
00405                 
00406                 smach.StateMachine.add('LearnerAddAction',
00407                                 LearnerAddAction(),
00408                                 transitions={'needs_learning':'MoveArmBaseAndWait',
00409                                                 'succeeded':'NeedInfo',
00410                                                 'preempted':'failedPlanning',
00411                                                 'aborted':'failedPlanning'})
00412                 
00413                 smach.StateMachine.add('MoveArmBase', MoveArmBase(), 
00414                                 transitions={'next':'NeedInfo', 
00415                                                 'failed':'failedMoveArm'})
00416                 
00417                 smach.StateMachine.add('MoveArmBaseAndWait', MoveArmBaseWait(), 
00418                                 transitions={'next':'WaitASecond', 
00419                                                 'failed':'failedMoveArm'})
00420                                                 
00421                 smach.StateMachine.add('WaitASecond', st_sleep.WaitSeconds(1),
00422                                 transitions={'finish':'NeedInfo'})
00423 
00424         # smach viewer
00425         sis = smach_ros.IntrospectionServer('iri_board_cleaning', sm, '/SM_LEARNING')
00426         sis.start()
00427         
00428         # Execute SMACH plan
00429         try:
00430                 outcome = sm.execute()
00431         finally:
00432                 sis.stop()
00433 
00434 
00435 
00436 if __name__ == '__main__':
00437         global time_perception
00438         global time_state
00439         global time_planning
00440         global time_learning
00441         global time_moving
00442         global time_extra_learn
00443         
00444         time_perception = 0
00445         time_state = 0
00446         time_planning = 0
00447         time_learning = 0
00448         time_moving = 0
00449         time_extra_learn = 0
00450         
00451         start=time.time()
00452         main()
00453         finish=time.time()
00454         total_time = finish-start
00455         rospy.loginfo('Time taken: ' + str(total_time))
00456         print "Total time " + str(total_time)
00457         
00458         
00459         
00460         rospy.loginfo('Time taken perception: ' + str(time_perception))
00461         rospy.loginfo('Time taken state: ' + str(time_state))
00462         rospy.loginfo('Time taken planning: ' + str(time_planning))
00463         rospy.loginfo('Time taken learning: ' + str(time_learning))
00464         rospy.loginfo('Time taken moving: ' + str(time_moving))
00465         rospy.loginfo('Time taken extra_learn: ' + str(time_extra_learn))


iri_clean_board
Author(s): David Martinez
autogenerated on Fri Dec 6 2013 23:52:37