Пример #1
0
class RobocupInteractiveMarker(object):
    def __init__(self, server):
        self.server = server
        self.pose = Pose()
        self.publish = True
        self.int_marker = None
        self.make_marker()
        self.menu_handler = MenuHandler()
        item = self.menu_handler.insert("publish", callback=self.menu_callback)
        self.menu_handler.setCheckState(item, MenuHandler.CHECKED)
        self.menu_handler.apply(self.server, self.marker_name)

    def feedback(self, feedback):
        self.pose = feedback.pose
        self.server.applyChanges()

    def menu_callback(self, feedback):
        item = feedback.menu_entry_id
        if self.menu_handler.getCheckState(item) == MenuHandler.CHECKED:
            self.menu_handler.setCheckState(item, MenuHandler.UNCHECKED)
            self.publish = False
        else:
            self.publish = True
            self.menu_handler.setCheckState(item, MenuHandler.CHECKED)

        self.menu_handler.reApply(self.server)
        self.server.applyChanges()

    def make_marker(self):
        self.int_marker = InteractiveMarker()
        self.int_marker.header.frame_id = "map"
        self.int_marker.pose = self.pose
        self.int_marker.scale = 1

        self.int_marker.name = self.marker_name

        control = InteractiveMarkerControl()
        control.orientation.w = math.sqrt(2) / 2
        control.orientation.x = 0
        control.orientation.y = math.sqrt(2) / 2
        control.orientation.z = 0
        control.interaction_mode = self.interaction_mode
        self.int_marker.controls.append(copy.deepcopy(control))

        # make a box which also moves in the plane
        markers = self.make_individual_markers(self.int_marker)
        for marker in markers:
            control.markers.append(marker)
        control.always_visible = True
        self.int_marker.controls.append(control)

        # we want to use our special callback function
        self.server.insert(self.int_marker, self.feedback)
Пример #2
0
class GripperMarkers:

    _offset = 0.09

    def __init__(self, side_prefix):
        self.ik = IK(side_prefix)

        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer('ik_request_markers')
        self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()

        self._menu_handler.insert('Move arm here',
                                  callback=self.move_to_pose_cb)

        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker')
        self._im_server.applyChanges()

        # Code for moving the robots joints
        switch_srv_name = 'pr2_controller_manager/switch_controller'
        rospy.loginfo('Waiting for switch controller service...')
        rospy.wait_for_service(switch_srv_name)
        self.switch_service_client = rospy.ServiceProxy(
            switch_srv_name, SwitchController)

        self.r_joint_names = [
            'r_shoulder_pan_joint', 'r_shoulder_lift_joint',
            'r_upper_arm_roll_joint', 'r_elbow_flex_joint',
            'r_forearm_roll_joint', 'r_wrist_flex_joint', 'r_wrist_roll_joint'
        ]

        self.l_joint_names = [
            'l_shoulder_pan_joint', 'l_shoulder_lift_joint',
            'l_upper_arm_roll_joint', 'l_elbow_flex_joint',
            'l_forearm_roll_joint', 'l_wrist_flex_joint', 'l_wrist_roll_joint'
        ]

        # Create a trajectory action client
        r_traj_controller_name = '/r_arm_controller/joint_trajectory_action'
        self.r_traj_action_client = SimpleActionClient(r_traj_controller_name,
                                                       JointTrajectoryAction)
        rospy.loginfo(
            'Waiting for a response from the trajectory action server for RIGHT arm...'
        )
        self.r_traj_action_client.wait_for_server()

        l_traj_controller_name = '/l_arm_controller/joint_trajectory_action'
        self.l_traj_action_client = SimpleActionClient(l_traj_controller_name,
                                                       JointTrajectoryAction)
        rospy.loginfo(
            'Waiting for a response from the trajectory action server for LEFT arm...'
        )
        self.l_traj_action_client.wait_for_server()

    def get_ee_pose(self):
        from_frame = 'base_link'
        to_frame = self.side_prefix + '_wrist_roll_link'
        try:

            t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)

            (pos,
             rot) = self._tf_listener.lookupTransform(from_frame, to_frame, t)

        except:

            rospy.logerr('Could not get end effector pose through TF.')
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

        return Pose(Point(pos[0], pos[1], pos[2]),
                    Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, dummy):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')
        joint_positions = self.ik.get_ik_for_ee(self.ee_pose)
        print 'joint: ' + str(joint_positions)
        if (joint_positions != None):
            self.toggle_arm(self.side_prefix, 'Freeze', False)
            #joint_positions = [-0.993560463247, -0.357041076593, 0.0534981848008, -1.24934444608, -3.10068096283, -1.7906747183, -28.4704855309]
            print 'returned from IK: ' + str(joint_positions)
            #print 'random position : ' + str([-0.993560463247, -0.357041076593, 0.0534981848008, -1.24934444608, -3.10068096283, -1.7906747183, -28.4704855309])
            #joint_positions = [-1.03129153, -0.35312086, -0.08, -1.25402906, -2.98718287, -1.7816027, 3.03965124]
            self.move_to_joints(self.side_prefix, list(joint_positions), 5.0)
        print 'done'

    def toggle_arm(self, side, toggle, button):
        controller_name = side + '_arm_controller'
        print 'toggle'
        start_controllers = []
        stop_controllers = []
        if (toggle == 'Relax'):
            stop_controllers.append(controller_name)
        else:
            start_controllers.append(controller_name)
        self.set_arm_mode(start_controllers, stop_controllers)

    def set_arm_mode(self, start_controllers, stop_controllers):
        try:
            self.switch_service_client(start_controllers, stop_controllers, 1)
        except rospy.ServiceException:
            rospy.logerr('Could not change arm mode.')

    def move_to_joints(self, side_prefix, positions, time_to_joint):
        '''Moves the arm to the desired joints'''
        velocities = [0] * len(positions)
        traj_goal = JointTrajectoryGoal()
        traj_goal.trajectory.header.stamp = (rospy.Time.now() +
                                             rospy.Duration(0.1))
        traj_goal.trajectory.points.append(
            JointTrajectoryPoint(
                positions=positions,
                velocities=velocities,
                time_from_start=rospy.Duration(time_to_joint)))
        if (side_prefix == 'r'):
            traj_goal.trajectory.joint_names = self.r_joint_names
            self.r_traj_action_client.send_goal(traj_goal)
        else:
            traj_goal.trajectory.joint_names = self.l_joint_names
            self.l_traj_action_client.send_goal(traj_goal)

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):

        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose

        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = 'x=' + str(pose.position.x) + ' y=' + str(
            pose.position.y) + ' x=' + str(pose.position.z)
        menu_control.markers.append(
            Marker(type=Marker.TEXT_VIEW_FACING,
                   id=0,
                   scale=Vector3(0, 0, 0.03),
                   text=text,
                   color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                   header=Header(frame_id=frame_id),
                   pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker'
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open = False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
            tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
            tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
        pos = transform[:3, 3].copy()
        rot = tf.transformations.quaternion_from_matrix(transform)
        return Pose(Point(pos[0], pos[1], pos[2]),
                    Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        mesh.color = ColorRGBA(0.0, 0.5, 1.0, 0.6)
        ik_solution = self.ik.get_ik_for_ee(self.ee_pose)
        if (ik_solution == None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #3
0
class ActionStepMarker:
    ''' Marker for visualizing the steps of an action'''

    _im_server = None
    _offset = 0.09
    _ref_object_list = None
    _ref_names = None
    _marker_click_cb = None

    def __init__(self, step_number, arm_index, action_step, marker_click_cb):

        if ActionStepMarker._im_server == None:
            im_server = InteractiveMarkerServer('programmed_actions')
            ActionStepMarker._im_server = im_server

        self.action_step = action_step
        self.arm_index = arm_index
        self.step_number = step_number
        self.is_requested = False
        self.is_deleted = False
        self.is_control_visible = False
        self.is_edited = False
        self.has_object = False

        self._sub_entries = None
        self._menu_handler = None
        ActionStepMarker._marker_click_cb = marker_click_cb

    def _is_reachable(self):
        '''Checks if there is an IK solution for action step'''
        dummy, is_reachable = Arms.solve_ik_for_arm(self.arm_index,
                                                    self.get_target())
        rospy.loginfo('Reachability of pose in ActionStepMarker : ' +
                      str(is_reachable))
        return is_reachable

    def get_uid(self):
        '''Returns a unique id of the marker'''
        return (2 * self.step_number + self.arm_index)

    def _get_name(self):
        '''Generates the unique name for the marker'''
        return ('step' + str(self.step_number) + 'arm' + str(self.arm_index))

    def decrease_id(self):
        '''Reduces the index of the marker'''
        self.step_number -= 1
        self._update_menu()

    def update_ref_frames(self, ref_frame_list):
        '''Updates and re-assigns coordinate frames when the world changes'''
        # There is a new list of objects
        # If the current frames are already assigned to object,
        # we need to figure out the correspondences
        ActionStepMarker._ref_object_list = ref_frame_list

        arm_pose = self.get_target()

        if (arm_pose.refFrame == ArmState.OBJECT):
            prev_ref_obj = arm_pose.refFrameObject
            new_ref_obj = World.get_most_similar_obj(prev_ref_obj,
                                                     ref_frame_list)
            self.has_object = False
            if (new_ref_obj != None):
                self.has_object = True
                arm_pose.refFrameObject = new_ref_obj

        ActionStepMarker._ref_names = ['base_link']
        for i in range(len(ActionStepMarker._ref_object_list)):
            ActionStepMarker._ref_names.append(
                ActionStepMarker._ref_object_list[i].name)

        self._update_menu()

    def destroy(self):
        '''Removes marker from the world'''
        ActionStepMarker._im_server.erase(self._get_name())
        ActionStepMarker._im_server.applyChanges()

    def _update_menu(self):
        '''Recreates the menu when something has changed'''
        self._menu_handler = MenuHandler()
        frame_entry = self._menu_handler.insert('Reference frame')
        self._sub_entries = [None] * len(ActionStepMarker._ref_names)
        for i in range(len(ActionStepMarker._ref_names)):
            self._sub_entries[i] = self._menu_handler.insert(
                ActionStepMarker._ref_names[i],
                parent=frame_entry,
                callback=self.change_ref_cb)
        self._menu_handler.insert('Move arm here', callback=self.move_to_cb)
        self._menu_handler.insert('Move to current arm pose',
                                  callback=self.move_pose_to_cb)
        self._menu_handler.insert('Delete', callback=self.delete_step_cb)
        for i in range(len(ActionStepMarker._ref_names)):
            self._menu_handler.setCheckState(self._sub_entries[i],
                                             MenuHandler.UNCHECKED)

        menu_id = self._get_menu_id(self._get_ref_name())
        if menu_id == None:
            self.has_object = False
        else:
            self._menu_handler.setCheckState(menu_id, MenuHandler.CHECKED)
        self._update_viz_core()
        self._menu_handler.apply(ActionStepMarker._im_server, self._get_name())
        ActionStepMarker._im_server.applyChanges()

    def _get_menu_id(self, ref_name):
        '''Returns the unique menu id from its name
        None if the object is not found'''
        if ref_name in ActionStepMarker._ref_names:
            index = ActionStepMarker._ref_names.index(ref_name)
            return self._sub_entries[index]
        else:
            return None

    def _get_menu_name(self, menu_id):
        '''Returns the menu name from its unique menu id'''
        index = self._sub_entries.index(menu_id)
        return ActionStepMarker._ref_names[index]

    def _get_ref_name(self):
        '''Returns the name string for the reference
        frame object of the action step'''

        ref_name = None
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTarget.rArm.refFrame
                ref_name = self.action_step.armTarget.rArm.refFrameObject.name
            else:
                ref_frame = self.action_step.armTarget.lArm.refFrame
                ref_name = self.action_step.armTarget.lArm.refFrameObject.name

        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTrajectory.rRefFrame
                ref_name = self.action_step.armTrajectory.rRefFrameObject.name
            else:
                ref_frame = self.action_step.armTrajectory.lRefFrame
                ref_name = self.action_step.armTrajectory.lRefFrameObject.name
        else:
            rospy.logerr('Unhandled marker type: ' +
                         str(self.action_step.type))

        if (ref_frame == ArmState.ROBOT_BASE):
            ref_name = 'base_link'

        return ref_name

    def _set_ref(self, new_ref_name):
        '''Changes the reference frame of the action step'''
        new_ref = World.get_ref_from_name(new_ref_name)
        if (new_ref != ArmState.ROBOT_BASE):
            index = ActionStepMarker._ref_names.index(new_ref_name)
            new_ref_obj = ActionStepMarker._ref_object_list[index - 1]
        else:
            new_ref_obj = Object()

        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = World.convert_ref_frame(
                    self.action_step.armTarget.rArm, new_ref, new_ref_obj)
            else:
                self.action_step.armTarget.lArm = World.convert_ref_frame(
                    self.action_step.armTarget.lArm, new_ref, new_ref_obj)
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            for i in range(len(self.action_step.armTrajectory.timing)):
                if self.arm_index == 0:
                    arm_old = self.action_step.armTrajectory.rArm[i]
                    arm_new = World.convert_ref_frame(arm_old, new_ref,
                                                      new_ref_obj)
                    self.action_step.armTrajectory.rArm[i] = arm_new
                else:
                    arm_old = self.action_step.armTrajectory.lArm[i]
                    arm_new = World.convert_ref_frame(arm_old, new_ref,
                                                      new_ref_obj)
                    self.action_step.armTrajectory.lArm[i] = arm_new
            if self.arm_index == 0:
                self.action_step.armTrajectory.rRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.rRefFrame = new_ref
            else:
                self.action_step.armTrajectory.lRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.lRefFrame = new_ref

    def _is_hand_open(self):
        '''Checks if the gripper is open for the action step'''
        if self.arm_index == 0:
            gripper_state = self.action_step.gripperAction.rGripper
        else:
            gripper_state = self.action_step.gripperAction.lGripper
        return (gripper_state == GripperState.OPEN)

    def set_new_pose(self, new_pose):
        '''Changes the pose of the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                pose = ActionStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.rArm.ee_pose = pose
            else:
                pose = ActionStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.lArm.ee_pose = pose
            self.update_viz()
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            rospy.logwarn('Modification of whole trajectory ' +
                          'segments is not implemented.')

    def get_absolute_position(self, is_start=True):
        '''Returns the absolute position of the action step'''
        pose = self.get_absolute_pose(is_start)
        return pose.position

    def get_absolute_pose(self, is_start=True):
        '''Returns the absolute pose of the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                arm_pose = self.action_step.armTarget.rArm
            else:
                arm_pose = self.action_step.armTarget.lArm

        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if is_start:
                    index = len(self.action_step.armTrajectory.rArm) - 1
                    arm_pose = self.action_step.armTrajectory.rArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.rArm[0]
            else:
                if is_start:
                    index = len(self.action_step.armTrajectory.lArm) - 1
                    arm_pose = self.action_step.armTrajectory.lArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.lArm[0]

        #if (arm_pose.refFrame == ArmState.OBJECT and
        #    World.has_object(arm_pose.refFrameObject.name)):
        #    return ActionStepMarker._offset_pose(arm_pose.ee_pose)
        #else:
        world_pose = World.get_absolute_pose(arm_pose)
        return ActionStepMarker._offset_pose(world_pose)

    def get_pose(self):
        '''Returns the pose of the action step'''
        target = self.get_target()
        if (target != None):
            return ActionStepMarker._offset_pose(target.ee_pose)

    @staticmethod
    def _offset_pose(pose, constant=1):
        '''Offsets the world pose for visualization'''
        transform = World.get_matrix_from_pose(pose)
        offset_array = [constant * ActionStepMarker._offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(
            transform, offset_transform)
        return World.get_pose_from_transform(hand_transform)

    def set_target(self, target):
        '''Sets the new pose for the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = target
            else:
                self.action_step.armTarget.lArm = target
            self.has_object = True
            self._update_menu()
        self.is_edited = False

    def get_target(self, traj_index=None):
        '''Returns the pose for the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                return self.action_step.armTarget.rArm
            else:
                return self.action_step.armTarget.lArm
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if traj_index == None:
                    traj = self.action_step.armTrajectory.rArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.rArm[traj_index]
            else:
                if traj_index == None:
                    traj = self.action_step.armTrajectory.lArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.lArm[traj_index]

    def _get_traj_pose(self, index):
        '''Returns a single pose for trajectory'''
        if (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                target = self.action_step.armTrajectory.rArm[index]
            else:
                target = self.action_step.armTrajectory.lArm[index]
            return target.ee_pose
        else:
            rospy.logerr('Cannot request trajectory pose ' +
                         'on non-trajectory action step.')

    def _update_viz_core(self):
        '''Updates visualization after a change'''
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = self._get_ref_name()
        pose = self.get_pose()

        if (self.action_step.type == ActionStep.ARM_TARGET):
            menu_control = self._make_gripper_marker(menu_control,
                                                     self._is_hand_open())
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            point_list = []
            for j in range(len(self.action_step.armTrajectory.timing)):
                point_list.append(self._get_traj_pose(j).position)

            main_marker = Marker(type=Marker.SPHERE_LIST,
                                 id=self.get_uid(),
                                 lifetime=rospy.Duration(2),
                                 scale=Vector3(0.02, 0.02, 0.02),
                                 header=Header(frame_id=frame_id),
                                 color=ColorRGBA(0.8, 0.4, 0.0, 0.8),
                                 points=point_list)
            menu_control.markers.append(main_marker)
            menu_control.markers.append(
                ActionStepMarker.make_sphere_marker(self.get_uid() + 2000,
                                                    self._get_traj_pose(0),
                                                    frame_id, 0.05))
            last_index = len(self.action_step.armTrajectory.timing) - 1
            menu_control.markers.append(
                ActionStepMarker.make_sphere_marker(
                    self.get_uid() + 3000, self._get_traj_pose(last_index),
                    frame_id, 0.05))
        else:
            rospy.logerr('Non-handled action step type ' +
                         str(self.action_step.type))

        ref_frame = World.get_ref_from_name(frame_id)
        if (ref_frame == ArmState.OBJECT):
            menu_control.markers.append(
                Marker(type=Marker.ARROW,
                       id=(1000 + self.get_uid()),
                       lifetime=rospy.Duration(2),
                       scale=Vector3(0.02, 0.03, 0.04),
                       header=Header(frame_id=frame_id),
                       color=ColorRGBA(1.0, 0.8, 0.2, 0.5),
                       points=[pose.position, Point(0, 0, 0)]))

        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        menu_control.markers.append(
            Marker(type=Marker.TEXT_VIEW_FACING,
                   id=self.get_uid(),
                   scale=Vector3(0, 0, 0.03),
                   text='Step' + str(self.step_number),
                   color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                   header=Header(frame_id=frame_id),
                   pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))

        int_marker = InteractiveMarker()
        int_marker.name = self._get_name()
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker, True)

        int_marker.controls.append(menu_control)
        ActionStepMarker._im_server.insert(int_marker, self.marker_feedback_cb)

    @staticmethod
    def make_sphere_marker(uid, pose, frame_id, radius):
        '''Creates a sphere marker'''
        return Marker(type=Marker.SPHERE,
                      id=uid,
                      lifetime=rospy.Duration(2),
                      scale=Vector3(radius, radius, radius),
                      pose=pose,
                      header=Header(frame_id=frame_id),
                      color=ColorRGBA(1.0, 0.5, 0.0, 0.8))

    def marker_feedback_cb(self, feedback):
        '''Callback for when an event occurs on the marker'''
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.set_new_pose(feedback.pose)
            self.update_viz()
        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            # Set the visibility of the 6DOF controller
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
            ActionStepMarker._marker_click_cb(self.get_uid(),
                                              self.is_control_visible)
        else:
            rospy.loginfo('Unknown event' + str(feedback.event_type))

    def delete_step_cb(self, dummy):
        '''Callback for when delete is requested'''
        self.is_deleted = True

    def move_to_cb(self, dummy):
        '''Callback for when moving to a pose is requested'''
        self.is_requested = True

    def move_pose_to_cb(self, dummy):
        '''Callback for when a pose change to current is requested'''
        self.is_edited = True

    def pose_reached(self):
        '''Update when a requested pose is reached'''
        self.is_requested = False

    def change_ref_cb(self, feedback):
        '''Callback for when a reference frame change is requested'''
        self._menu_handler.setCheckState(
            self._get_menu_id(self._get_ref_name()), MenuHandler.UNCHECKED)
        self._menu_handler.setCheckState(feedback.menu_entry_id,
                                         MenuHandler.CHECKED)
        new_ref = self._get_menu_name(feedback.menu_entry_id)
        self._set_ref(new_ref)
        rospy.loginfo('Switching reference frame to ' + new_ref +
                      ' for action step ' + self._get_name())
        self._menu_handler.reApply(ActionStepMarker._im_server)
        ActionStepMarker._im_server.applyChanges()
        self.update_viz()

    def update_viz(self):
        '''Updates visualization fully'''
        self._update_viz_core()
        self._menu_handler.reApply(ActionStepMarker._im_server)
        ActionStepMarker._im_server.applyChanges()

    def _add_6dof_marker(self, int_marker, is_fixed):
        '''Adds a 6 DoF control marker to the interactive marker'''
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        '''Creates one component of the 6dof controller'''
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control

    def _make_mesh_marker(self):
        '''Creates a mesh marker'''
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        if self._is_reachable():
            mesh.color = ColorRGBA(1.0, 0.5, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.5, 0.5, 0.5, 0.6)
        return mesh

    def _make_gripper_marker(self, control, is_hand_open=False):
        '''Makes a gripper marker'''
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0

        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - ActionStepMarker._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)

        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -ActionStepMarker._offset
        mesh1.pose.orientation.w = 1

        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh2.pose = World.get_pose_from_transform(t_proximal)

        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh3.pose = World.get_pose_from_transform(t_distal)

        quat = tf.transformations.quaternion_multiply(
            tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
            tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - ActionStepMarker._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)

        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh4.pose = World.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh5.pose = World.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)

        return control
Пример #4
0
        help='Output folder to where the collected data will be stored.',
        type=str,
        required=True)
    ap.add_argument("-c",
                    "--calibration_file",
                    help='full path to calibration file.',
                    type=str,
                    required=True)
    args = vars(ap.parse_args())

    # Initialize ROS stuff
    rospy.init_node("collect_and_label")
    # rospack = rospkg.RosPack()  # get an instance of RosPack with the default search paths
    server = InteractiveMarkerServer("data_labeler")
    robot_description = rospy.get_param('/robot_description')
    rospy.sleep(0.5)

    # Process robot description and create an instance of class Sensor for each sensor
    data_collector = DataCollectorAndLabeler(args['output_folder'], server,
                                             menu_handler,
                                             args['marker_scale'],
                                             args['calibration_file'])

    createInteractiveMarker(data_collector.world_link)
    initMenu()
    menu_handler.reApply(server)
    server.applyChanges()
    print('Changes applied ...')

    rospy.spin()
Пример #5
0
class GripperMarkers:

    _offset = 0.09

    def __init__(self, side_prefix):

        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer('ik_request_markers_' +
                                                  self.side_prefix)
        self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()

        self._menu_handler.insert('Move arm here',
                                  callback=self.move_to_pose_cb)

        self.r_joint_names = [
            'r_shoulder_pan_joint', 'r_shoulder_lift_joint',
            'r_upper_arm_roll_joint', 'r_elbow_flex_joint',
            'r_forearm_roll_joint', 'r_wrist_flex_joint', 'r_wrist_roll_joint'
        ]
        self.l_joint_names = [
            'l_shoulder_pan_joint', 'l_shoulder_lift_joint',
            'l_upper_arm_roll_joint', 'l_elbow_flex_joint',
            'l_forearm_roll_joint', 'l_wrist_flex_joint', 'l_wrist_roll_joint'
        ]

        # Create a trajectory action client
        r_traj_contoller_name = None
        l_traj_contoller_name = None
        if self.side_prefix == 'r':
            r_traj_controller_name = '/r_arm_controller/joint_trajectory_action'
            self.r_traj_action_client = SimpleActionClient(
                r_traj_controller_name, JointTrajectoryAction)
            rospy.loginfo('Waiting for a response from the trajectory ' +
                          'action server for RIGHT arm...')
            self.r_traj_action_client.wait_for_server()

        else:
            l_traj_controller_name = '/l_arm_controller/joint_trajectory_action'
            self.l_traj_action_client = SimpleActionClient(
                l_traj_controller_name, JointTrajectoryAction)
            rospy.loginfo('Waiting for a response from the trajectory ' +
                          'action server for LEFT arm...')
            self.l_traj_action_client.wait_for_server()

        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.ik = IK(side_prefix)
        self.update_viz()
        self._menu_handler.apply(self._im_server,
                                 'ik_target_marker_' + self.side_prefix)
        self._im_server.applyChanges()
        print self.ik

    def get_ee_pose(self):
        from_frame = 'base_link'
        to_frame = self.side_prefix + '_wrist_roll_link'
        try:
            if self._tf_listener.frameExists(
                    from_frame) and self._tf_listener.frameExists(to_frame):
                t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)
                # t = rospy.Time.now()
                (pos, rot) = self._tf_listener.lookupTransform(
                    to_frame, from_frame, t)  # Note argument order :(
            else:
                rospy.logerr(
                    'TF frames do not exist; could not get end effector pose.')
        except Exception as err:
            rospy.logerr('Could not get end effector pose through TF.')
            rospy.logerr(err)
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

        return Pose(Point(pos[0], pos[1], pos[2]),
                    Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, feedback):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')
        '''Moves the arm to the desired joints'''
        print feedback
        time_to_joint = 2.0
        positions = self.ik.get_ik_for_ee(feedback.pose)
        velocities = [0] * len(positions)
        traj_goal = JointTrajectoryGoal()
        traj_goal.trajectory.header.stamp = (rospy.Time.now() +
                                             rospy.Duration(0.1))
        traj_goal.trajectory.points.append(
            JointTrajectoryPoint(
                positions=positions,
                velocities=velocities,
                time_from_start=rospy.Duration(time_to_joint)))

        if (self.side_prefix == 'r'):
            traj_goal.trajectory.joint_names = self.r_joint_names
            self.r_traj_action_client.send_goal(traj_goal)
        else:
            traj_goal.trajectory.joint_names = self.l_joint_names
            self.l_traj_action_client.send_goal(traj_goal)
        pass

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose

        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = 'x=' + str(pose.position.x) + ' y=' + str(
            pose.position.y) + ' x=' + str(pose.position.z)
        menu_control.markers.append(
            Marker(type=Marker.TEXT_VIEW_FACING,
                   id=0,
                   scale=Vector3(0, 0, 0.03),
                   text=text,
                   color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                   header=Header(frame_id=frame_id),
                   pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker_' + self.side_prefix
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open = False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
            tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
            tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(
            transform1, transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = (
            'package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
        pos = transform[:3, 3].copy()
        rot = tf.transformations.quaternion_from_matrix(transform)
        return Pose(Point(pos[0], pos[1], pos[2]),
                    Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        print self
        ik_solution = self.ik.get_ik_for_ee(self.ee_pose)
        if (ik_solution is None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1),
                                          False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1),
                                          True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #6
0
class ActionStepMarker:
    ''' Marker for visualizing the steps of an action'''

    _im_server = None
    _offset = 0.09
    _ref_object_list = None
    _ref_names = None
    _marker_click_cb = None

    def __init__(self, step_number, arm_index, action_step,
                 marker_click_cb):

        if ActionStepMarker._im_server == None:
            im_server = InteractiveMarkerServer('programmed_actions')
            ActionStepMarker._im_server = im_server

        self.action_step = action_step
        self.arm_index = arm_index
        self.step_number = step_number
        self.is_requested = False
        self.is_deleted = False
        self.is_control_visible = False
        self.is_edited = False
        self.has_object = False

        self._sub_entries = None
        self._menu_handler = None
        ActionStepMarker._marker_click_cb = marker_click_cb

    def _is_reachable(self):
        '''Checks if there is an IK solution for action step'''
        dummy, is_reachable = Arms.solve_ik_for_arm(self.arm_index,
                                                    self.get_target())
        rospy.loginfo('Reachability of pose in ActionStepMarker : ' +
            str(is_reachable))
        return is_reachable

    def get_uid(self):
        '''Returns a unique id of the marker'''
        return (2 * self.step_number + self.arm_index)

    def _get_name(self):
        '''Generates the unique name for the marker'''
        return ('step' + str(self.step_number)
                                        + 'arm' + str(self.arm_index))

    def decrease_id(self):
        '''Reduces the index of the marker'''
        self.step_number -= 1
        self._update_menu()

    def update_ref_frames(self, ref_frame_list):
        '''Updates and re-assigns coordinate frames when the world changes'''
        # There is a new list of objects
        # If the current frames are already assigned to object,
        # we need to figure out the correspondences
        ActionStepMarker._ref_object_list = ref_frame_list

        arm_pose = self.get_target()

        if (arm_pose.refFrame == ArmState.OBJECT):
            prev_ref_obj = arm_pose.refFrameObject
            new_ref_obj = World.get_most_similar_obj(prev_ref_obj,
                                                    ref_frame_list)
            self.has_object = False
            if (new_ref_obj != None):
                self.has_object = True
                arm_pose.refFrameObject = new_ref_obj

        ActionStepMarker._ref_names = ['base_link']
        for i in range(len(ActionStepMarker._ref_object_list)):
            ActionStepMarker._ref_names.append(
                            ActionStepMarker._ref_object_list[i].name)

        self._update_menu()

    def destroy(self):
        '''Removes marker from the world'''
        ActionStepMarker._im_server.erase(self._get_name())
        ActionStepMarker._im_server.applyChanges()

    def _update_menu(self):
        '''Recreates the menu when something has changed'''
        self._menu_handler = MenuHandler()
        frame_entry = self._menu_handler.insert('Reference frame')
        self._sub_entries = [None] * len(ActionStepMarker._ref_names)
        for i in range(len(ActionStepMarker._ref_names)):
            self._sub_entries[i] = self._menu_handler.insert(
                            ActionStepMarker._ref_names[i], parent=frame_entry,
                            callback=self.change_ref_cb)
        self._menu_handler.insert('Move arm here', callback=self.move_to_cb)
        self._menu_handler.insert('Move to current arm pose',
                            callback=self.move_pose_to_cb)
        self._menu_handler.insert('Delete', callback=self.delete_step_cb)
        for i in range(len(ActionStepMarker._ref_names)):
            self._menu_handler.setCheckState(self._sub_entries[i],
                                            MenuHandler.UNCHECKED)

        menu_id = self._get_menu_id(self._get_ref_name())
        if menu_id == None:
            self.has_object = False
        else:
            self._menu_handler.setCheckState(menu_id,
                            MenuHandler.CHECKED)
        self._update_viz_core()
        self._menu_handler.apply(ActionStepMarker._im_server, self._get_name())
        ActionStepMarker._im_server.applyChanges()

    def _get_menu_id(self, ref_name):
        '''Returns the unique menu id from its name
        None if the object is not found'''
        if ref_name in ActionStepMarker._ref_names:
            index = ActionStepMarker._ref_names.index(ref_name)
            return self._sub_entries[index]
        else:
            return None

    def _get_menu_name(self, menu_id):
        '''Returns the menu name from its unique menu id'''
        index = self._sub_entries.index(menu_id)
        return ActionStepMarker._ref_names[index]

    def _get_ref_name(self):
        '''Returns the name string for the reference
        frame object of the action step'''

        ref_name = None
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTarget.rArm.refFrame
                ref_name = self.action_step.armTarget.rArm.refFrameObject.name
            else:
                ref_frame = self.action_step.armTarget.lArm.refFrame
                ref_name = self.action_step.armTarget.lArm.refFrameObject.name

        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTrajectory.rRefFrame
                ref_name = self.action_step.armTrajectory.rRefFrameObject.name
            else:
                ref_frame = self.action_step.armTrajectory.lRefFrame
                ref_name = self.action_step.armTrajectory.lRefFrameObject.name
        else:
            rospy.logerr('Unhandled marker type: ' +
                                        str(self.action_step.type))

        if (ref_frame == ArmState.ROBOT_BASE):
            ref_name = 'base_link'

        return ref_name

    def _set_ref(self, new_ref_name):
        '''Changes the reference frame of the action step'''
        new_ref = World.get_ref_from_name(new_ref_name)
        if (new_ref != ArmState.ROBOT_BASE):
            index = ActionStepMarker._ref_names.index(new_ref_name)
            new_ref_obj = ActionStepMarker._ref_object_list[index - 1]
        else:
            new_ref_obj = Object()

        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = World.convert_ref_frame(
                        self.action_step.armTarget.rArm, new_ref, new_ref_obj)
            else:
                self.action_step.armTarget.lArm = World.convert_ref_frame(
                        self.action_step.armTarget.lArm, new_ref, new_ref_obj)
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            for i in range(len(self.action_step.armTrajectory.timing)):
                if self.arm_index == 0:
                    arm_old = self.action_step.armTrajectory.rArm[i]
                    arm_new = World.convert_ref_frame(arm_old,
                                                      new_ref, new_ref_obj)
                    self.action_step.armTrajectory.rArm[i] = arm_new
                else:
                    arm_old = self.action_step.armTrajectory.lArm[i]
                    arm_new = World.convert_ref_frame(arm_old,
                                                      new_ref, new_ref_obj)
                    self.action_step.armTrajectory.lArm[i] = arm_new
            if self.arm_index == 0:
                self.action_step.armTrajectory.rRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.rRefFrame = new_ref
            else:
                self.action_step.armTrajectory.lRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.lRefFrame = new_ref

    def _is_hand_open(self):
        '''Checks if the gripper is open for the action step'''
        if self.arm_index == 0:
            gripper_state = self.action_step.gripperAction.rGripper
        else:
            gripper_state = self.action_step.gripperAction.lGripper
        return (gripper_state == GripperState.OPEN)

    def set_new_pose(self, new_pose):
        '''Changes the pose of the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                pose = ActionStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.rArm.ee_pose = pose
            else:
                pose = ActionStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.lArm.ee_pose = pose
            self.update_viz()
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            rospy.logwarn('Modification of whole trajectory ' +
                          'segments is not implemented.')

    def get_absolute_position(self, is_start=True):
        '''Returns the absolute position of the action step'''
        pose = self.get_absolute_pose(is_start)
        return pose.position

    def get_absolute_pose(self, is_start=True):
        '''Returns the absolute pose of the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                arm_pose = self.action_step.armTarget.rArm
            else:
                arm_pose = self.action_step.armTarget.lArm

        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if is_start:
                    index = len(self.action_step.armTrajectory.rArm) - 1
                    arm_pose = self.action_step.armTrajectory.rArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.rArm[0]
            else:
                if is_start:
                    index = len(self.action_step.armTrajectory.lArm) - 1
                    arm_pose = self.action_step.armTrajectory.lArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.lArm[0]

        #if (arm_pose.refFrame == ArmState.OBJECT and
        #    World.has_object(arm_pose.refFrameObject.name)):
        #    return ActionStepMarker._offset_pose(arm_pose.ee_pose)
        #else:
        world_pose = World.get_absolute_pose(arm_pose)
        return ActionStepMarker._offset_pose(world_pose)

    def get_pose(self):
        '''Returns the pose of the action step'''
        target = self.get_target()
        if (target != None):
            return ActionStepMarker._offset_pose(target.ee_pose)

    @staticmethod
    def _offset_pose(pose, constant=1):
        '''Offsets the world pose for visualization'''
        transform = World.get_matrix_from_pose(pose)
        offset_array = [constant * ActionStepMarker._offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform,
                                                        offset_transform)
        return World.get_pose_from_transform(hand_transform)

    def set_target(self, target):
        '''Sets the new pose for the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = target
            else:
                self.action_step.armTarget.lArm = target
            self.has_object = True
            self._update_menu()
        self.is_edited = False

    def get_target(self, traj_index=None):
        '''Returns the pose for the action step'''
        if (self.action_step.type == ActionStep.ARM_TARGET):
            if self.arm_index == 0:
                return self.action_step.armTarget.rArm
            else:
                return self.action_step.armTarget.lArm
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if traj_index == None:
                    traj = self.action_step.armTrajectory.rArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.rArm[traj_index]
            else:
                if traj_index == None:
                    traj = self.action_step.armTrajectory.lArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.lArm[traj_index]

    def _get_traj_pose(self, index):
        '''Returns a single pose for trajectory'''
        if (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            if self.arm_index == 0:
                target = self.action_step.armTrajectory.rArm[index]
            else:
                target = self.action_step.armTrajectory.lArm[index]
            return target.ee_pose
        else:
            rospy.logerr('Cannot request trajectory pose ' +
                         'on non-trajectory action step.')

    def _update_viz_core(self):
        '''Updates visualization after a change'''
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = self._get_ref_name()
        pose = self.get_pose()

        if (self.action_step.type == ActionStep.ARM_TARGET):
            menu_control = self._make_gripper_marker(menu_control,
                                                  self._is_hand_open())
        elif (self.action_step.type == ActionStep.ARM_TRAJECTORY):
            point_list = []
            for j in range(len(self.action_step.armTrajectory.timing)):
                point_list.append(self._get_traj_pose(j).position)

            main_marker = Marker(type=Marker.SPHERE_LIST, id=self.get_uid(),
                                lifetime=rospy.Duration(2),
                                scale=Vector3(0.02, 0.02, 0.02),
                                header=Header(frame_id=frame_id),
                                color=ColorRGBA(0.8, 0.4, 0.0, 0.8),
                                points=point_list)
            menu_control.markers.append(main_marker)
            menu_control.markers.append(ActionStepMarker.make_sphere_marker(
                                self.get_uid() + 2000,
                                self._get_traj_pose(0), frame_id, 0.05))
            last_index = len(self.action_step.armTrajectory.timing) - 1
            menu_control.markers.append(ActionStepMarker.make_sphere_marker(
                self.get_uid() + 3000, self._get_traj_pose(last_index),
                frame_id, 0.05))
        else:
            rospy.logerr('Non-handled action step type '
                         + str(self.action_step.type))

        ref_frame = World.get_ref_from_name(frame_id)
        if (ref_frame == ArmState.OBJECT):
            menu_control.markers.append(Marker(type=Marker.ARROW,
                        id=(1000 + self.get_uid()),
                        lifetime=rospy.Duration(2),
                        scale=Vector3(0.02, 0.03, 0.04),
                        header=Header(frame_id=frame_id),
                        color=ColorRGBA(1.0, 0.8, 0.2, 0.5),
                        points=[pose.position, Point(0, 0, 0)]))

        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                        id=self.get_uid(), scale=Vector3(0, 0, 0.03),
                        text='Step' + str(self.step_number),
                        color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                        header=Header(frame_id=frame_id),
                        pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))

        int_marker = InteractiveMarker()
        int_marker.name = self._get_name()
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker, True)

        int_marker.controls.append(menu_control)
        ActionStepMarker._im_server.insert(int_marker,
                                           self.marker_feedback_cb)

    @staticmethod
    def make_sphere_marker(uid, pose, frame_id, radius):
        '''Creates a sphere marker'''
        return Marker(type=Marker.SPHERE, id=uid, lifetime=rospy.Duration(2),
                        scale=Vector3(radius, radius, radius),
                        pose=pose, header=Header(frame_id=frame_id),
                        color=ColorRGBA(1.0, 0.5, 0.0, 0.8))

    def marker_feedback_cb(self, feedback):
        '''Callback for when an event occurs on the marker'''
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.set_new_pose(feedback.pose)
            self.update_viz()
        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            # Set the visibility of the 6DOF controller
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
            ActionStepMarker._marker_click_cb(self.get_uid(),
                                              self.is_control_visible)
        else:
            rospy.loginfo('Unknown event' + str(feedback.event_type))

    def delete_step_cb(self, dummy):
        '''Callback for when delete is requested'''
        self.is_deleted = True

    def move_to_cb(self, dummy):
        '''Callback for when moving to a pose is requested'''
        self.is_requested = True

    def move_pose_to_cb(self, dummy):
        '''Callback for when a pose change to current is requested'''
        self.is_edited = True

    def pose_reached(self):
        '''Update when a requested pose is reached'''
        self.is_requested = False

    def change_ref_cb(self, feedback):
        '''Callback for when a reference frame change is requested'''
        self._menu_handler.setCheckState(
                    self._get_menu_id(self._get_ref_name()),
                    MenuHandler.UNCHECKED)
        self._menu_handler.setCheckState(feedback.menu_entry_id,
                    MenuHandler.CHECKED)
        new_ref = self._get_menu_name(feedback.menu_entry_id)
        self._set_ref(new_ref)
        rospy.loginfo('Switching reference frame to '
                      + new_ref + ' for action step ' + self._get_name())
        self._menu_handler.reApply(ActionStepMarker._im_server)
        ActionStepMarker._im_server.applyChanges()
        self.update_viz()

    def update_viz(self):
        '''Updates visualization fully'''
        self._update_viz_core()
        self._menu_handler.reApply(ActionStepMarker._im_server)
        ActionStepMarker._im_server.applyChanges()

    def _add_6dof_marker(self, int_marker, is_fixed):
        '''Adds a 6 DoF control marker to the interactive marker'''
        control = self._make_6dof_control('rotate_x',
                        Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x',
                        Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z',
                        Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z',
                        Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y',
                        Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y',
                        Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        '''Creates one component of the 6dof controller'''
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control

    def _make_mesh_marker(self):
        '''Creates a mesh marker'''
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        if self._is_reachable():
            mesh.color = ColorRGBA(1.0, 0.5, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.5, 0.5, 0.5, 0.6)
        return mesh

    def _make_gripper_marker(self, control, is_hand_open=False):
        '''Makes a gripper marker'''
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0

        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - ActionStepMarker._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,
                                                           transform2)

        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/' +
                                'gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -ActionStepMarker._offset
        mesh1.pose.orientation.w = 1

        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh2.pose = World.get_pose_from_transform(t_proximal)

        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh3.pose = World.get_pose_from_transform(t_distal)

        quat = tf.transformations.quaternion_multiply(
                    tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
                    tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - ActionStepMarker._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,
                                                           transform2)

        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh4.pose = World.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh5.pose = World.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)

        return control
Пример #7
0
class GripperMarkers:

    _offset = 0.09
    def __init__(self, side_prefix):
        
        self.ik = IK(side_prefix)
        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer('ik_request_markers')
        self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()
        self._menu_handler.insert('Move arm here', callback=self.move_to_pose_cb)
        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker')
        self._im_server.applyChanges()

    def get_ee_pose(self):
        from_frame = '/base_link'
        to_frame = '/' + self.side_prefix + '_wrist_roll_link'
        try:
            t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)
            (pos, rot) = self._tf_listener.lookupTransform(from_frame, to_frame, t)
        except:
            rospy.logwarn('Could not get end effector pose through TF.')
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

	return Pose(Point(pos[0], pos[1], pos[2]),
			Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, dummy):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')

        target_pose = GripperMarkers._offset_pose(self.ee_pose)
        ik_solution = self.ik.get_ik_for_ee(target_pose)
    
        #TODO: Send the arms to ik_solution

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):
        
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose
        
        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = 'x=' + str(pose.position.x) + ' y=' + str(pose.position.y) + ' x=' + str(pose.position.z)
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.03),
                                           text=text,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker'
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open=False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
        tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
        tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
		pos = transform[:3,3].copy()
		rot = tf.transformations.quaternion_from_matrix(transform)
		return Pose(Point(pos[0], pos[1], pos[2]),
				Quaternion(rot[0], rot[1], rot[2], rot[3]))

    @staticmethod
    def _offset_pose(pose):
        transform = GripperMarkers.get_matrix_from_pose(pose)
        offset_array = [GripperMarkers._offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform, offset_transform)
        return GripperMarkers.get_pose_from_transform(hand_transform)

    @staticmethod
    def get_matrix_from_pose(pose):
        rotation = [pose.orientation.x, pose.orientation.y,
                pose.orientation.z, pose.orientation.w]
        transformation = tf.transformations.quaternion_matrix(rotation)
        position = [pose.position.x, pose.position.y, pose.position.z]
        transformation[:3, 3] = position
        return transformation

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
    	mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        
        target_pose = GripperMarkers._offset_pose(self.ee_pose)
        ik_solution = self.ik.get_ik_for_ee(target_pose)
        
        if (ik_solution == None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
            mesh.color = ColorRGBA(0.0, 0.5, 1.0, 0.6)

        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #8
0
class GripperMarkers:

    _offset = -0.09
    _tf_listener = None

    def __init__(self, side_prefix):
        
        if GripperMarkers._tf_listener is None:
	    GripperMarkers._tf_listener = TransformListener()

        self.ik = IK(side_prefix)
        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer(side_prefix + '_ik_request_markers')
        self._menu_handler = MenuHandler()
        self._menu_handler.insert('Move arm here', callback=self.move_to_pose_cb)
        self.is_control_visible = False
        self.marker_pose = self._offset_pose(self.get_ee_pose(), -GripperMarkers._offset)
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker')
        self._im_server.applyChanges()

    def get_ee_pose(self):
        from_frame = '/base_link'
        to_frame = '/' + self.side_prefix + '_wrist_roll_link'
        try:
	    GripperMarkers._tf_listener.waitForTransform(from_frame, to_frame, rospy.Time(0), rospy.Duration(5))
            t = GripperMarkers._tf_listener.getLatestCommonTime(from_frame, to_frame)
            (pos, rot) = GripperMarkers._tf_listener.lookupTransform(from_frame, to_frame, t)
        except:
            rospy.logwarn('Could not get end effector pose through TF.')
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

	return Pose(Point(pos[0], pos[1], pos[2]),
			Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, dummy):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')

        target_pose = GripperMarkers._offset_pose(self.marker_pose, GripperMarkers._offset)
        ik_solution = self.ik.get_ik_for_ee(target_pose)
        
        if (ik_solution == None):
            rospy.logwarn('No IK solutions for this pose, cannot move.')
        else:
            self.ik.move_to_joints(ik_solution, 2.0)
        pass

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.marker_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):
        
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.marker_pose
        
        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        #text = 'x=' + str(pose.position.x) + ' y=' + str(pose.position.y) + ' x=' + str(pose.position.z)
	text = self.side_prefix + '_arm'
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.05),
                                           text=text,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker'
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open=False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
	offset = -GripperMarkers._offset
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
        tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
        tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
	pos = transform[:3,3].copy()
	rot = tf.transformations.quaternion_from_matrix(transform)
	return Pose(Point(pos[0], pos[1], pos[2]),
			Quaternion(rot[0], rot[1], rot[2], rot[3]))

    @staticmethod
    def _offset_pose(pose, x_offset):
        transform = GripperMarkers.get_matrix_from_pose(pose)
        offset_array = [x_offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform,
                                                             offset_transform)
    	return GripperMarkers.get_pose_from_transform(hand_transform)

    @staticmethod
    def get_matrix_from_pose(pose):
        rotation = [pose.orientation.x, pose.orientation.y,
                pose.orientation.z, pose.orientation.w]
        transformation = tf.transformations.quaternion_matrix(rotation)
        position = [pose.position.x, pose.position.y, pose.position.z]
        transformation[:3, 3] = position
        return transformation

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
    	mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        
        target_pose = GripperMarkers._offset_pose(self.marker_pose, GripperMarkers._offset)
        ik_solution = self.ik.get_ik_for_ee(target_pose)
        
        if (ik_solution == None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)

        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #9
0
class GripperMarkers:

    _offset = 0.09
    def __init__(self, side_prefix):
        self._ik_service = IK(side_prefix)

        r_traj_controller_name = '/r_arm_controller/joint_trajectory_action'
        self.r_traj_action_client = SimpleActionClient(r_traj_controller_name, JointTrajectoryAction)
        rospy.loginfo('Waiting for a response from the trajectory action server for RIGHT arm...')
        self.r_traj_action_client.wait_for_server()

        l_traj_controller_name = '/l_arm_controller/joint_trajectory_action'
        self.l_traj_action_client = SimpleActionClient(l_traj_controller_name, JointTrajectoryAction)
        rospy.loginfo('Waiting for a response from the trajectory action server for LEFT arm...')
        self.l_traj_action_client.wait_for_server()

        self.r_joint_names = ['r_shoulder_pan_joint',
                              'r_shoulder_lift_joint',
                              'r_upper_arm_roll_joint',
                              'r_elbow_flex_joint',
                              'r_forearm_roll_joint',
                              'r_wrist_flex_joint',
                              'r_wrist_roll_joint']
        self.l_joint_names = ['l_shoulder_pan_joint',
                              'l_shoulder_lift_joint',
                              'l_upper_arm_roll_joint',
                              'l_elbow_flex_joint',
                              'l_forearm_roll_joint',
                              'l_wrist_flex_joint',
                              'l_wrist_roll_joint']

        rospy.Subscriber('ar_pose_marker', AlvarMarkers, self.marker_cb)
	
	self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer("ik_request_markers_{}".format(side_prefix))
	self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()

        self._menu_handler.insert("Move {} arm here".format(side_prefix), callback=self.move_to_pose_cb)

        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker')
        self._im_server.applyChanges()

    def get_ee_pose(self):
	from_frame = '/base_link'
	to_frame = '/' + self.side_prefix + '_wrist_roll_link'
	try:
	    t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)
	    (pos, rot) = self._tf_listener.lookupTransform(from_frame, to_frame, t)
	except Exception as e:
	    rospy.logerr('Could not get end effector pose through TF.')
	    pos = [1.0, 0.0, 1.0]
	    rot = [0.0, 0.0, 0.0, 1.0]
	    import traceback
 	    traceback.print_exc()


	return Pose(Point(pos[0], pos[1], pos[2]),
			Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, dummy):
        target_pose = GripperMarkers._offset_pose(self.ee_pose)
        ik_sol = self._ik_service.get_ik_for_ee(target_pose)
        self.move_to_joints(self.side_prefix, [ik_sol], 1.0)

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def marker_cb(self, pose_markers):
        rospy.loginfo('AR Marker Pose updating')
        transform = GripperMarkers.get_matrix_from_pose(pose_markers.markers[0].pose.pose)
        offset_array = [0, 0, .03]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform,
                                                             offset_transform)
        self.ee_pose = GripperMarkers.get_pose_from_transform(hand_transform)
        self.update_viz() 

    def update_viz(self):
        
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose
        
        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = "x=%.3f y=%.3f z=%.3f" % (pose.position.x, pose.position.y, pose.position.z)
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.03),
                                           text=text,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        label_pos = Point()
        label_pos.x = pose.position.x
        label_pos.y = pose.position.y
        label_pos.z = pose.position.z
        label = "{} arm".format(self.side_prefix)
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.03),
                                           text=label,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.9),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(label_pos, Quaternion(0, 0, 0, 1))))

        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker'
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open=False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
            tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
            tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def _offset_pose(pose):
        transform = GripperMarkers.get_matrix_from_pose(pose)
        offset_array = [-GripperMarkers._offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform,
                                                             offset_transform)
        return GripperMarkers.get_pose_from_transform(hand_transform)

    @staticmethod
    def get_matrix_from_pose(pose):
        rotation = [pose.orientation.x, pose.orientation.y,
                pose.orientation.z, pose.orientation.w]
        transformation = tf.transformations.quaternion_matrix(rotation)
        position = [pose.position.x, pose.position.y, pose.position.z]
        transformation[:3, 3] = position
        return transformation

    @staticmethod
    def get_pose_from_transform(transform):
	pos = transform[:3,3].copy()
	rot = tf.transformations.quaternion_from_matrix(transform)
	return Pose(Point(pos[0], pos[1], pos[2]),
			Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
    	mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0

        target_pose = GripperMarkers._offset_pose(self.ee_pose)
        ik_sol = self._ik_service.get_ik_for_ee(target_pose)
        if ik_sol == None:
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control

    def move_to_joints(self, side_prefix, positions, time_to_joint):
        '''Moves the arm to the desired joints'''
        traj_goal = JointTrajectoryGoal()
        traj_goal.trajectory.header.stamp = (rospy.Time.now() + rospy.Duration(0.1))
        time_move = time_to_joint
        print "using following positions %s" % positions
        for pose in positions:
            velocities = [0] * len(pose)
            traj_goal.trajectory.points.append(JointTrajectoryPoint(positions=pose,
                            velocities=velocities, time_from_start=rospy.Duration(time_move)))
            time_move += time_to_joint

        if (side_prefix == 'r'):
            traj_goal.trajectory.joint_names = self.r_joint_names
            self.r_traj_action_client.send_goal(traj_goal)
        else:
            traj_goal.trajectory.joint_names = self.l_joint_names
            self.l_traj_action_client.send_goal(traj_goal)
class GripperMarkers:

    _offset = 0.09
    def __init__(self, side_prefix):
        self.ik = IK(side_prefix)
	
        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer('ik_request_markers')
        self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()

        self._menu_handler.insert('Move arm here', callback=self.move_to_pose_cb)

        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker')
        self._im_server.applyChanges()
        
        # Code for moving the robots joints
        switch_srv_name = 'pr2_controller_manager/switch_controller'
        rospy.loginfo('Waiting for switch controller service...')
        rospy.wait_for_service(switch_srv_name)
        self.switch_service_client = rospy.ServiceProxy(switch_srv_name,
                                                 SwitchController)
                                                 
        self.r_joint_names = ['r_shoulder_pan_joint',
                              'r_shoulder_lift_joint',
                              'r_upper_arm_roll_joint',
                              'r_elbow_flex_joint',
                              'r_forearm_roll_joint',
                              'r_wrist_flex_joint',
                              'r_wrist_roll_joint']
                              
        self.l_joint_names = ['l_shoulder_pan_joint',
                              'l_shoulder_lift_joint',
                              'l_upper_arm_roll_joint',
                              'l_elbow_flex_joint',
                              'l_forearm_roll_joint',
                              'l_wrist_flex_joint',
                              'l_wrist_roll_joint']
                              
        # Create a trajectory action client
        r_traj_controller_name = '/r_arm_controller/joint_trajectory_action'
        self.r_traj_action_client = SimpleActionClient(r_traj_controller_name, JointTrajectoryAction)
        rospy.loginfo('Waiting for a response from the trajectory action server for RIGHT arm...')
        self.r_traj_action_client.wait_for_server()
        
        l_traj_controller_name = '/l_arm_controller/joint_trajectory_action'
        self.l_traj_action_client = SimpleActionClient(l_traj_controller_name, JointTrajectoryAction)
        rospy.loginfo('Waiting for a response from the trajectory action server for LEFT arm...')
        self.l_traj_action_client.wait_for_server()

    def get_ee_pose(self):
        from_frame = 'base_link'
        to_frame = self.side_prefix + '_wrist_roll_link'
        try:
           
            t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)
 
            (pos, rot) = self._tf_listener.lookupTransform(from_frame, to_frame, t)

        except:

            rospy.logerr('Could not get end effector pose through TF.')
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

        
        return Pose(Point(pos[0], pos[1], pos[2]),
               Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, dummy):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')
        joint_positions = self.ik.get_ik_for_ee(self.ee_pose)
        print 'joint: ' + str(joint_positions)
        if(joint_positions != None):
            self.toggle_arm(self.side_prefix, 'Freeze', False)
            #joint_positions = [-0.993560463247, -0.357041076593, 0.0534981848008, -1.24934444608, -3.10068096283, -1.7906747183, -28.4704855309]
            print 'returned from IK: ' + str(joint_positions)
            #print 'random position : ' + str([-0.993560463247, -0.357041076593, 0.0534981848008, -1.24934444608, -3.10068096283, -1.7906747183, -28.4704855309])
            #joint_positions = [-1.03129153, -0.35312086, -0.08, -1.25402906, -2.98718287, -1.7816027, 3.03965124]
            self.move_to_joints(self.side_prefix, list(joint_positions), 5.0)
        print 'done'
        
    def toggle_arm(self, side, toggle, button):
        controller_name = side + '_arm_controller'
        print 'toggle'
        start_controllers = []
        stop_controllers = []
        if (toggle == 'Relax'):
            stop_controllers.append(controller_name)
        else:
            start_controllers.append(controller_name)
        self.set_arm_mode(start_controllers, stop_controllers)

    def set_arm_mode(self, start_controllers, stop_controllers):
        try:
            self.switch_service_client(start_controllers, stop_controllers, 1)
        except rospy.ServiceException:
            rospy.logerr('Could not change arm mode.')
       
    def move_to_joints(self, side_prefix, positions, time_to_joint):
        '''Moves the arm to the desired joints'''
        velocities = [0] * len(positions)
        traj_goal = JointTrajectoryGoal()
        traj_goal.trajectory.header.stamp = (rospy.Time.now() + rospy.Duration(0.1))
        traj_goal.trajectory.points.append(JointTrajectoryPoint(positions=positions,
                            velocities=velocities, time_from_start=rospy.Duration(time_to_joint)))
        if (side_prefix == 'r'):
            traj_goal.trajectory.joint_names = self.r_joint_names
            self.r_traj_action_client.send_goal(traj_goal)
        else:
            traj_goal.trajectory.joint_names = self.l_joint_names
            self.l_traj_action_client.send_goal(traj_goal)

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):
        
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose
        
        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = 'x=' + str(pose.position.x) + ' y=' + str(pose.position.y) + ' x=' + str(pose.position.z)
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.03),
                                           text=text,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker'
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open=False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
        tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
        tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
        pos = transform[:3,3].copy()
        rot = tf.transformations.quaternion_from_matrix(transform)
        return Pose(Point(pos[0], pos[1], pos[2]),
                    Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
    	mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        mesh.color = ColorRGBA(0.0, 0.5, 1.0, 0.6)
        ik_solution = self.ik.get_ik_for_ee(self.ee_pose)
        if (ik_solution == None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #11
0
class GripperMarkers:

    _offset = 0.09
    def __init__(self, side_prefix):

        
        self.side_prefix = side_prefix
        self._im_server = InteractiveMarkerServer('ik_request_markers_' + self.side_prefix)
        self._tf_listener = TransformListener()
        self._menu_handler = MenuHandler()

        self._menu_handler.insert('Move arm here', callback=self.move_to_pose_cb)

        self.r_joint_names = ['r_shoulder_pan_joint',
                              'r_shoulder_lift_joint',
                              'r_upper_arm_roll_joint',
                              'r_elbow_flex_joint',
                              'r_forearm_roll_joint',
                              'r_wrist_flex_joint',
                              'r_wrist_roll_joint']
        self.l_joint_names = ['l_shoulder_pan_joint',
                              'l_shoulder_lift_joint',
                              'l_upper_arm_roll_joint',
                              'l_elbow_flex_joint',
                              'l_forearm_roll_joint',
                              'l_wrist_flex_joint',
                              'l_wrist_roll_joint']

        # Create a trajectory action client
        r_traj_contoller_name = None
        l_traj_contoller_name = None
        if self.side_prefix == 'r':
                r_traj_controller_name = '/r_arm_controller/joint_trajectory_action'
                self.r_traj_action_client = SimpleActionClient(r_traj_controller_name,
                        JointTrajectoryAction)
                rospy.loginfo('Waiting for a response from the trajectory '
                        + 'action server for RIGHT arm...')
                self.r_traj_action_client.wait_for_server()
        
        else:
                l_traj_controller_name = '/l_arm_controller/joint_trajectory_action'
                self.l_traj_action_client = SimpleActionClient(l_traj_controller_name,
                        JointTrajectoryAction)
                rospy.loginfo('Waiting for a response from the trajectory '
                        + 'action server for LEFT arm...')
                self.l_traj_action_client.wait_for_server()

        self.is_control_visible = False
        self.ee_pose = self.get_ee_pose()
        self.ik = IK(side_prefix)
        self.update_viz()
        self._menu_handler.apply(self._im_server, 'ik_target_marker_' + self.side_prefix)
        self._im_server.applyChanges()
        print self.ik

    def get_ee_pose(self):
        from_frame = 'base_link'
        to_frame = self.side_prefix + '_wrist_roll_link'
        try:
            if self._tf_listener.frameExists(from_frame) and self._tf_listener.frameExists(to_frame):
                t = self._tf_listener.getLatestCommonTime(from_frame, to_frame)
                # t = rospy.Time.now()
                (pos, rot) = self._tf_listener.lookupTransform(to_frame, from_frame, t) # Note argument order :(
            else:
                rospy.logerr('TF frames do not exist; could not get end effector pose.')
        except Exception as err:
            rospy.logerr('Could not get end effector pose through TF.')
            rospy.logerr(err)
            pos = [1.0, 0.0, 1.0]
            rot = [0.0, 0.0, 0.0, 1.0]

        return Pose(Point(pos[0], pos[1], pos[2]),
                Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def move_to_pose_cb(self, feedback):
        rospy.loginfo('You pressed the `Move arm here` button from the menu.')
        '''Moves the arm to the desired joints'''
        print feedback
        time_to_joint = 2.0
        positions = self.ik.get_ik_for_ee(feedback.pose)
        velocities = [0] * len(positions)
        traj_goal = JointTrajectoryGoal()
        traj_goal.trajectory.header.stamp = (rospy.Time.now() + rospy.Duration(0.1))
        traj_goal.trajectory.points.append(JointTrajectoryPoint(positions=positions,
                            velocities=velocities, time_from_start=rospy.Duration(time_to_joint)))
        
        if (self.side_prefix == 'r'):
            traj_goal.trajectory.joint_names = self.r_joint_names
            self.r_traj_action_client.send_goal(traj_goal)
        else:
            traj_goal.trajectory.joint_names = self.l_joint_names
            self.l_traj_action_client.send_goal(traj_goal)
        pass

    def marker_clicked_cb(self, feedback):
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.ee_pose = feedback.pose
            self.update_viz()
            self._menu_handler.reApply(self._im_server)
            self._im_server.applyChanges()

        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
        else:
            rospy.loginfo('Unhandled event: ' + str(feedback.event_type))

    def update_viz(self):
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = 'base_link'
        pose = self.ee_pose
        
        menu_control = self._add_gripper_marker(menu_control)
        text_pos = Point()
        text_pos.x = pose.position.x
        text_pos.y = pose.position.y
        text_pos.z = pose.position.z + 0.1
        text = 'x=' + str(pose.position.x) + ' y=' + str(pose.position.y) + ' x=' + str(pose.position.z)
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                                           id=0, scale=Vector3(0, 0, 0.03),
                                           text=text,
                                           color=ColorRGBA(0.0, 0.0, 0.0, 0.5),
                                           header=Header(frame_id=frame_id),
                                           pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))
        int_marker = InteractiveMarker()
        int_marker.name = 'ik_target_marker_' + self.side_prefix
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker)
        int_marker.controls.append(menu_control)
        self._im_server.insert(int_marker, self.marker_clicked_cb)

    def _add_gripper_marker(self, control):
        is_hand_open=False
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0
        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1, transform2)
        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -GripperMarkers._offset
        mesh1.pose.orientation.w = 1
        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh2.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh3.pose = GripperMarkers.get_pose_from_transform(t_distal)
        quat = tf.transformations.quaternion_multiply(
        tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
        tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - GripperMarkers._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,transform2)
        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger.dae')
        mesh4.pose = GripperMarkers.get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/gripper_v0/l_finger_tip.dae')
        mesh5.pose = GripperMarkers.get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)
        return control

    @staticmethod
    def get_pose_from_transform(transform):
        pos = transform[:3,3].copy()
        rot = tf.transformations.quaternion_from_matrix(transform)
        return Pose(Point(pos[0], pos[1], pos[2]),
                Quaternion(rot[0], rot[1], rot[2], rot[3]))

    def _make_mesh_marker(self):
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        print self
        ik_solution = self.ik.get_ik_for_ee(self.ee_pose)
        if (ik_solution is None):
            mesh.color = ColorRGBA(1.0, 0.0, 0.0, 0.6)
        else:
            mesh.color = ColorRGBA(0.0, 1.0, 0.0, 0.6)
        return mesh

    def _add_6dof_marker(self, int_marker):
        is_fixed = True
        control = self._make_6dof_control('rotate_x', Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x', Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z', Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z', Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y', Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y', Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control
Пример #12
0
class ArmStepMarker:
    ''' Marker for visualizing the steps of an action'''

    _offset = 0.09
    _marker_click_cb = None
    _reference_change_cb = None

    def __init__(self, step_number, arm_index, action_step,
                 marker_click_cb, reference_change_cb, parent_sequence):
        self.action_step = action_step
        self.arm_index = arm_index
        self.step_number = step_number
        self.is_requested = False
        self.is_deleted = False
        self.is_control_visible = False
        self.is_edited = False
        self.has_object = False
        self.is_dimmed = False
        self.is_fake = False

        self._sub_entries = None
        self._menu_handler = None
        ArmStepMarker._marker_click_cb = marker_click_cb
        ArmStepMarker._reference_change_cb = reference_change_cb

        self.parent_step_sequence = parent_sequence

    def _is_reachable(self):
        '''Checks if there is an IK solution for action step'''
        dummy, is_reachable = Robot.solve_ik_for_arm(self.arm_index,
                                                    self.get_target())
        # rospy.loginfo('Reachability of pose in ArmStepMarker : ' +
        #     str(is_reachable))
        return is_reachable

    def get_uid(self):
        '''Returns a unique id of the marker'''
        return (2 * self.step_number + self.arm_index)

    def _get_name(self):
        '''Generates the unique name for the marker'''
        return ('step' + str(self.step_number)
                                        + 'arm' + str(self.arm_index))

    def decrease_id(self):
        '''Reduces the index of the marker'''
        self.step_number -= 1
        self._update_menu()

    def update_ref_frames(self, ref_frame_list, new_ref_obj):
        '''Updates and re-assigns coordinate frames when the world changes'''
        # There is a new list of objects
        # If the current frames are already assigned to object,
        # we need to figure out the correspondences
        self.parent_step_sequence.ref_object_list = ref_frame_list

        arm_pose = self.get_target()

        if (arm_pose.refFrame == ArmState.OBJECT):
            self.has_object = False
            if (new_ref_obj != None):
                self.has_object = True
                arm_pose.refFrameObject = new_ref_obj

        self.parent_step_sequence.ref_names = ['base_link']
        for i in range(len(self.parent_step_sequence.ref_object_list)):
            self.parent_step_sequence.ref_names.append(
                            self.parent_step_sequence.ref_object_list[i].name)

        self._update_menu()

    def destroy(self):
        '''Removes marker from the world'''
        self.parent_step_sequence.im_server.erase(self._get_name())
        self.parent_step_sequence.im_server.applyChanges()

    def _update_menu(self):
        '''Recreates the menu when something has changed'''
        self._menu_handler = MenuHandler()
        frame_entry = self._menu_handler.insert('Reference frame')
        self._sub_entries = [None] * len(self.parent_step_sequence.ref_names)
        for i in range(len(self.parent_step_sequence.ref_names)):
            self._sub_entries[i] = self._menu_handler.insert(
                            self.parent_step_sequence.ref_names[i], parent=frame_entry,
                            callback=self.change_ref_cb)
        self._menu_handler.insert('Move arm here', callback=self.move_to_cb)
        self._menu_handler.insert('Move to current arm pose',
                            callback=self.move_pose_to_cb)
        self._menu_handler.insert('Delete', callback=self.delete_step_cb)
        for i in range(len(self.parent_step_sequence.ref_names)):
            self._menu_handler.setCheckState(self._sub_entries[i],
                                            MenuHandler.UNCHECKED)

        menu_id = self._get_menu_id(self._get_ref_name())
        if menu_id is None:
            self.has_object = False
        else:
            self._menu_handler.setCheckState(menu_id,
                            MenuHandler.CHECKED)
        self._update_viz_core()
        self._menu_handler.apply(self.parent_step_sequence.im_server, self._get_name())
        self.parent_step_sequence.im_server.applyChanges()

    def _get_menu_id(self, ref_name):
        '''Returns the unique menu id from its name
        None if the object is not found'''
        if ref_name in self.parent_step_sequence.ref_names:
            index = self.parent_step_sequence.ref_names.index(ref_name)
            return self._sub_entries[index]
        else:
            return None

    def _get_menu_name(self, menu_id):
        '''Returns the menu name from its unique menu id'''
        index = self._sub_entries.index(menu_id)
        return self.parent_step_sequence.ref_names[index]

    def _get_ref_name(self):
        '''Returns the name string for the reference
        frame object of the action step'''

        ref_name = None
        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTarget.rArm.refFrame
                ref_name = self.action_step.armTarget.rArm.refFrameObject.name
            else:
                ref_frame = self.action_step.armTarget.lArm.refFrame
                ref_name = self.action_step.armTarget.lArm.refFrameObject.name

        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            if self.arm_index == 0:
                ref_frame = self.action_step.armTrajectory.rRefFrame
                ref_name = self.action_step.armTrajectory.rRefFrameOject.name
            else:
                ref_frame = self.action_step.armTrajectory.lRefFrame
                ref_name = self.action_step.armTrajectory.lRefFrameOject.name
        else:
            rospy.logerr('Unhandled marker type: ' +
                                        str(self.action_step.type))

        if (ref_frame == ArmState.ROBOT_BASE):
            ref_name = 'base_link'

        return ref_name

    def _set_ref(self, new_ref_name):
        '''Changes the reference frame of the action step'''
        new_ref = World.get_world().get_ref_from_name(new_ref_name)
        if (new_ref != ArmState.ROBOT_BASE):
            index = self.parent_step_sequence.ref_names.index(new_ref_name)
            new_ref_obj = self.parent_step_sequence.ref_object_list[index - 1]
        else:
            new_ref_obj = Object()

        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = World.get_world().convert_ref_frame(
                        self.action_step.armTarget.rArm, new_ref, new_ref_obj)
            else:
                self.action_step.armTarget.lArm = World.get_world().convert_ref_frame(
                        self.action_step.armTarget.lArm, new_ref, new_ref_obj)
        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            for i in range(len(self.action_step.armTrajectory.timing)):
                if self.arm_index == 0:
                    arm_old = self.action_step.armTrajectory.rArm[i]
                    arm_new = World.get_world().convert_ref_frame(arm_old,
                                                      new_ref, new_ref_obj)
                    self.action_step.armTrajectory.rArm[i] = arm_new
                else:
                    arm_old = self.action_step.armTrajectory.lArm[i]
                    arm_new = World.get_world().convert_ref_frame(arm_old,
                                                      new_ref, new_ref_obj)
                    self.action_step.armTrajectory.lArm[i] = arm_new
            if self.arm_index == 0:
                self.action_step.armTrajectory.rRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.rRefFrame = new_ref
            else:
                self.action_step.armTrajectory.lRefFrameObject = new_ref_obj
                self.action_step.armTrajectory.lRefFrame = new_ref
        ArmStepMarker._reference_change_cb(self.get_uid(), new_ref, new_ref_obj)

    def _is_hand_open(self):
        '''Checks if the gripper is open for the action step'''
        if self.arm_index == 0:
            gripper_state = self.action_step.gripperAction.rGripper
        else:
            gripper_state = self.action_step.gripperAction.lGripper
        return (gripper_state == GripperState.OPEN)

    def set_new_pose(self, new_pose):
        '''Changes the pose of the action step'''
        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                pose = ArmStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.rArm.ee_pose = pose
            else:
                pose = ArmStepMarker._offset_pose(new_pose, -1)
                self.action_step.armTarget.lArm.ee_pose = pose
            rospy.loginfo('Set new pose for action step.')
            self.update_viz()
        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            rospy.logwarn('Modification of whole trajectory ' +
                          'segments is not implemented.')

    def get_absolute_position(self, is_start=True):
        '''Returns the absolute position of the action step'''
        pose = self.get_absolute_pose(is_start)
        return pose.position

    def get_absolute_pose(self, is_start=True):
        '''Returns the absolute pose of the action step'''
        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                arm_pose = self.action_step.armTarget.rArm
            else:
                arm_pose = self.action_step.armTarget.lArm

        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if is_start:
                    index = len(self.action_step.armTrajectory.rArm) - 1
                    arm_pose = self.action_step.armTrajectory.rArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.rArm[0]
            else:
                if is_start:
                    index = len(self.action_step.armTrajectory.lArm) - 1
                    arm_pose = self.action_step.armTrajectory.lArm[index]
                else:
                    arm_pose = self.action_step.armTrajectory.lArm[0]

        #if (arm_pose.refFrame == ArmState.OBJECT and
        #    World.has_object(arm_pose.refFrameObject.name)):
        #    return ArmStepMarker._offset_pose(arm_pose.ee_pose)
        #else:
        world_pose = World.get_world().get_absolute_pose(arm_pose)
        return ArmStepMarker._offset_pose(world_pose)

    def get_pose(self):
        '''Returns the pose of the action step'''
        target = self.get_target()
        if (target != None):
            return ArmStepMarker._offset_pose(target.ee_pose)

    @staticmethod
    def _offset_pose(pose, constant=1):
        '''Offsets the world pose for visualization'''
        transform = World.get_world().get_matrix_from_pose(pose)
        offset_array = [constant * ArmStepMarker._offset, 0, 0]
        offset_transform = tf.transformations.translation_matrix(offset_array)
        hand_transform = tf.transformations.concatenate_matrices(transform,
                                                        offset_transform)
        return World.get_world().get_pose_from_transform(hand_transform)

    def set_target(self, target):
        '''Sets the new pose for the action step'''
        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                self.action_step.armTarget.rArm = target
            else:
                self.action_step.armTarget.lArm = target
            self.has_object = True
            self._update_menu()
        self.is_edited = False

    def get_target(self, traj_index=None):
        '''Returns the pose for the action step'''
        if (self.action_step.type == ArmStepType.ARM_TARGET):
            if self.arm_index == 0:
                return self.action_step.armTarget.rArm
            else:
                return self.action_step.armTarget.lArm
        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            if self.arm_index == 0:
                if traj_index is None:
                    traj = self.action_step.armTrajectory.rArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.rArm[traj_index]
            else:
                if traj_index is None:
                    traj = self.action_step.armTrajectory.lArm
                    traj_index = int(len(traj) / 2)
                return self.action_step.armTrajectory.lArm[traj_index]

    def _get_traj_pose(self, index):
        '''Returns a single pose for trajectory'''
        if (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            if self.arm_index == 0:
                target = self.action_step.armTrajectory.rArm[index]
            else:
                target = self.action_step.armTrajectory.lArm[index]
            return target.ee_pose
        else:
            rospy.logerr('Cannot request trajectory pose ' +
                         'on non-trajectory action step.')

    def _update_viz_core(self):
        '''Updates visualization after a change'''
        menu_control = InteractiveMarkerControl()
        menu_control.interaction_mode = InteractiveMarkerControl.BUTTON
        menu_control.always_visible = True
        frame_id = self._get_ref_name()
        pose = self.get_pose()

        if (self.action_step.type == ArmStepType.ARM_TARGET):
            menu_control = self._make_gripper_marker(menu_control,
                                                  self._is_hand_open())
        elif (self.action_step.type == ArmStepType.ARM_TRAJECTORY):
            point_list = []
            for j in range(len(self.action_step.armTrajectory.timing)):
                point_list.append(self._get_traj_pose(j).position)

            main_marker = Marker(type=Marker.SPHERE_LIST, id=self.get_uid(),
                                lifetime=rospy.Duration(2),
                                scale=Vector3(0.02, 0.02, 0.02),
                                header=Header(frame_id=frame_id),
                                color=ColorRGBA(0.8, 0.4, 0.0, 0.8),
                                points=point_list)
            menu_control.markers.append(main_marker)
            menu_control.markers.append(ArmStepMarker.make_sphere_marker(
                                self.get_uid() + 2000,
                                self._get_traj_pose(0), frame_id, 0.05))
            last_index = len(self.action_step.armTrajectory.timing) - 1
            menu_control.markers.append(ArmStepMarker.make_sphere_marker(
                self.get_uid() + 3000, self._get_traj_pose(last_index),
                frame_id, 0.05))
        else:
            rospy.logerr('Non-handled action step type '
                         + str(self.action_step.type))

        ref_frame = World.get_world().get_ref_from_name(frame_id)
        if (ref_frame == ArmState.OBJECT):
            # The following is needed to properly display the arrtow in browser, due to the fact that ros3djs
            # displays all nested markers in the reference frame of the interactive marker.
            # Thus, we need to calculate the position of the object in the reference frame of the interactive marker.
            quat = [pose.orientation.x, pose.orientation.y, pose.orientation.z, pose.orientation.w]
            inv_quat_matrix = quaternion_matrix(quaternion_inverse(quat))
            pose_vec = numpy.array((pose.position.x, pose.position.y, pose.position.z, 0))
            new_pose = numpy.dot(inv_quat_matrix, pose_vec)
            menu_control.markers.append(Marker(type=Marker.ARROW,
                        id=(1000 + self.get_uid()),
                        lifetime=rospy.Duration(2),
                        scale=Vector3(0.01, 0.01, 0.0001),
                        header=Header(frame_id=frame_id),
                        color=ColorRGBA(0.8, 0.8, 0.0, 0.6),
                        points=[Point(0, 0, 0), Point(-new_pose[0], -new_pose[1], -new_pose[2])]))

        # Calculate text position so that they "orbit" around the marker;
        # this is done so that poses in identical or similar positions
        # have non-overlapping text. Note that to do this without moving
        # the text around as the camera is moved, we assume that the viewer
        # is always looking directly at the robot, so we assume the x dimension
        # is constant and "orbin" in the y-z plane.
        n_orbitals = 8 # this should be a constant
        offset = 0.15 # this should be a constant        
        orbital = (self.step_number - 1) % n_orbitals # - 1 to make 0-based
        angle_rad = (float(orbital) / n_orbitals) * (-2 * numpy.pi) + \
            (numpy.pi / 2.0) # start above, at pi/2 (90 degrees)
        text_pos = Point()
        text_pos.x = 0
        text_pos.y = numpy.cos(angle_rad) * offset
        text_pos.z = numpy.sin(angle_rad) * offset
        r,g,b = self.get_marker_color()
        menu_control.markers.append(Marker(type=Marker.TEXT_VIEW_FACING,
                        id=self.get_uid(), scale=Vector3(0.06, 0.06, 0.06),
                        lifetime=rospy.Duration(1.5),
                        text='Step ' + str(self.step_number),
                        color=ColorRGBA(r, g, b, 1.0),
                        header=Header(frame_id=frame_id),
                        pose=Pose(text_pos, Quaternion(0, 0, 0, 1))))

        int_marker = InteractiveMarker()
        int_marker.name = self._get_name()
        int_marker.header.frame_id = frame_id
        int_marker.pose = pose
        int_marker.scale = 0.2
        self._add_6dof_marker(int_marker, True)

        int_marker.controls.append(menu_control)
        self.parent_step_sequence.im_server.insert(int_marker,
                                           self.marker_feedback_cb)

    @staticmethod
    def make_sphere_marker(uid, pose, frame_id, radius):
        '''Creates a sphere marker'''
        return Marker(type=Marker.SPHERE, id=uid, lifetime=rospy.Duration(2),
                        scale=Vector3(radius, radius, radius),
                        pose=pose, header=Header(frame_id=frame_id),
                        color=ColorRGBA(1.0, 0.5, 0.0, 0.8))

    def marker_feedback_cb(self, feedback):
        '''Callback for when an event occurs on the marker'''
        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:
            self.set_new_pose(feedback.pose)
            self.update_viz()
        elif feedback.event_type == InteractiveMarkerFeedback.BUTTON_CLICK:
            # Set the visibility of the 6DOF controller
            rospy.loginfo('Changing visibility of the pose controls.')
            if (self.is_control_visible):
                self.is_control_visible = False
            else:
                self.is_control_visible = True
            ArmStepMarker._marker_click_cb(self.get_uid(),
                                              self.is_control_visible)
        else:
            rospy.loginfo('Unknown event' + str(feedback.event_type))

    def delete_step_cb(self, dummy):
        '''Callback for when delete is requested'''
        self.is_deleted = True

    def move_to_cb(self, dummy):
        '''Callback for when moving to a pose is requested'''
        self.is_requested = True

    def move_pose_to_cb(self, dummy):
        '''Callback for when a pose change to current is requested'''
        self.is_edited = True

    def pose_reached(self):
        '''Update when a requested pose is reached'''
        self.is_requested = False

    def change_ref_cb(self, feedback):
        '''Callback for when a reference frame change is requested'''
        self._menu_handler.setCheckState(
                    self._get_menu_id(self._get_ref_name()),
                    MenuHandler.UNCHECKED)
        self._menu_handler.setCheckState(feedback.menu_entry_id,
                    MenuHandler.CHECKED)
        new_ref = self._get_menu_name(feedback.menu_entry_id)
        self._set_ref(new_ref)
        rospy.loginfo('Switching reference frame to '
                      + new_ref + ' for action step ' + self._get_name())
        self._menu_handler.reApply(self.parent_step_sequence.im_server)
        self.parent_step_sequence.im_server.applyChanges()
        self.update_viz()

    def update_viz(self):
        '''Updates visualization fully'''
        self._update_viz_core()
        self._menu_handler.reApply(self.parent_step_sequence.im_server)
        self.parent_step_sequence.im_server.applyChanges()

    def _add_6dof_marker(self, int_marker, is_fixed):
        '''Adds a 6 DoF control marker to the interactive marker'''
        control = self._make_6dof_control('rotate_x',
                        Quaternion(1, 0, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_x',
                        Quaternion(1, 0, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_z',
                        Quaternion(0, 1, 0, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_z',
                        Quaternion(0, 1, 0, 1), True, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('rotate_y',
                        Quaternion(0, 0, 1, 1), False, is_fixed)
        int_marker.controls.append(control)
        control = self._make_6dof_control('move_y',
                        Quaternion(0, 0, 1, 1), True, is_fixed)
        int_marker.controls.append(control)

    def _make_6dof_control(self, name, orientation, is_move, is_fixed):
        '''Creates one component of the 6dof controller'''
        control = InteractiveMarkerControl()
        control.name = name
        control.orientation = orientation
        control.always_visible = False
        if (self.is_control_visible):
            if is_move:
                control.interaction_mode = InteractiveMarkerControl.MOVE_AXIS
            else:
                control.interaction_mode = InteractiveMarkerControl.ROTATE_AXIS
        else:
            control.interaction_mode = InteractiveMarkerControl.NONE
        if is_fixed:
            control.orientation_mode = InteractiveMarkerControl.FIXED
        return control


    def get_marker_color(self):
        '''Makes marker colors in a gradient according to the progression set in
        _get_rgb_from_abs_pos() (below).

        returns (r,g,b) tuple, each from 0.0 to 1.0
        '''
        total = self.parent_step_sequence.total_n_markers
        # These are 1-based indexing; turn them into 0-based indexing.
        idx = self.step_number - 1

        # First calculate "absolute" color position, plotting on a 0.0 - 1.0
        # scale. This only applies if there's more than one step; otherwise we
        # set to 0.0 (though it could be anything, as it just gets multiplied
        # by 0, as the idx must be 0 if there's only one step total).
        abs_step_size = 1.0 / float(total - 1) if total > 1 else 0.0
        abs_pos = abs_step_size * idx

        # Then, use our helper method to turn this into an RGB value.
        return self._get_rgb_from_abs_pos(abs_pos)


    def _get_rgb_from_abs_pos(self, abs_pos):
        '''Turns abs_pos, a float from 0.0 to 1.0 inclusive, into an rgb value
        of the range currently programmed. The progression is as follows (in
        order to avoid green hues, which could be confused with the objects),
        by gradient "bucket" step:
        - 0 yellow (start) -> red
        - 1 red -> purple
        - 2 purple -> blue
        - 3 blue -> cyan (end)

        Returns (r,g,b) tuple of floats, each from 0.0 to 1.0 inclusive.'''
        # Bucket settings (make constant)
        bucket = self.arm_index
        bucket_pos = abs_pos

        # Now translate to colors; todo later implement with better data
        # structure.
        r = 0.0
        g = 0.0
        b = 0.0
        if bucket == 0:
            # yellow -> red
            r = 1.0 
            g = 1.0 - bucket_pos
        elif bucket == 1:
            # cyan -> blue
            g = 1.0 - bucket_pos
            b = 1.0
        else:
            # Set white as error color
            rospy.logwarn("Bad color gradient; bucket " + str(bucket) +
                " and bucket position " + str(bucket_pos))
            r,g,b = 1.0, 1.0, 1.0

        return (r,g,b)


    def _make_mesh_marker(self):
        '''Creates a mesh marker'''
        mesh = Marker()
        mesh.mesh_use_embedded_materials = False
        mesh.type = Marker.MESH_RESOURCE
        mesh.scale.x = 1.0
        mesh.scale.y = 1.0
        mesh.scale.z = 1.0
        alpha = 0.6
        if self.is_dimmed:
            alpha = 0.1
        if self.is_fake:
            alpha = 0.4
            mesh.color = ColorRGBA(0.3, 0.3, 0.3, alpha)
            return mesh
        if self._is_reachable():
            # Original: some kinda orange
            # r,g,b = 1.0, 0.5, 0.0

            # New: rainbow! See method comment for details.
            r,g,b = self.get_marker_color()

            mesh.color = ColorRGBA(r, g, b, alpha)
        else:
            mesh.color = ColorRGBA(0.5, 0.5, 0.5, alpha)
        return mesh

    def _make_gripper_marker(self, control, is_hand_open=False):
        '''Makes a gripper marker'''
        if is_hand_open:
            angle = 28 * numpy.pi / 180.0
        else:
            angle = 0

        transform1 = tf.transformations.euler_matrix(0, 0, angle)
        transform1[:3, 3] = [0.07691 - ArmStepMarker._offset, 0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,
                                                           transform2)

        mesh1 = self._make_mesh_marker()
        mesh1.mesh_resource = ('package://pr2_description/meshes/' +
                                'gripper_v0/gripper_palm.dae')
        mesh1.pose.position.x = -ArmStepMarker._offset
        mesh1.pose.orientation.w = 1

        mesh2 = self._make_mesh_marker()
        mesh2.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh2.pose = World.get_world().get_pose_from_transform(t_proximal)

        mesh3 = self._make_mesh_marker()
        mesh3.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh3.pose = World.get_world().get_pose_from_transform(t_distal)

        quat = tf.transformations.quaternion_multiply(
                    tf.transformations.quaternion_from_euler(numpy.pi, 0, 0),
                    tf.transformations.quaternion_from_euler(0, 0, angle))
        transform1 = tf.transformations.quaternion_matrix(quat)
        transform1[:3, 3] = [0.07691 - ArmStepMarker._offset, -0.01, 0]
        transform2 = tf.transformations.euler_matrix(0, 0, -angle)
        transform2[:3, 3] = [0.09137, 0.00495, 0]
        t_proximal = transform1
        t_distal = tf.transformations.concatenate_matrices(transform1,
                                                           transform2)

        mesh4 = self._make_mesh_marker()
        mesh4.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger.dae')
        mesh4.pose = World.get_world().get_pose_from_transform(t_proximal)
        mesh5 = self._make_mesh_marker()
        mesh5.mesh_resource = ('package://pr2_description/meshes/' +
                               'gripper_v0/l_finger_tip.dae')
        mesh5.pose = World.get_world().get_pose_from_transform(t_distal)

        control.markers.append(mesh1)
        control.markers.append(mesh2)
        control.markers.append(mesh3)
        control.markers.append(mesh4)
        control.markers.append(mesh5)

        return control
Пример #13
0
class IntCollisionEnv(CollisionEnvServices):
    def __init__(self, setup, world_frame):

        super(IntCollisionEnv, self).__init__(setup, world_frame)

        self.im_server = InteractiveMarkerServer(self.NS + "markers")

        self.check_attached_timer = rospy.Timer(rospy.Duration(0.1),
                                                self.check_attached_timer_cb)

        self.create_menus()

    def create_menus(self):

        self.global_menu_handler = MenuHandler()
        g_art = self.global_menu_handler.insert("Artificial")
        self.global_menu_handler.insert("Add primitive",
                                        parent=g_art,
                                        callback=self.global_menu_add_prim_cb)
        self.global_menu_handler.insert("Clear all",
                                        parent=g_art,
                                        callback=self.global_menu_clear_all_cb)
        self.global_menu_handler.insert(
            "Clear all (permanent)",
            parent=g_art,
            callback=self.global_menu_clear_all_perm_cb)
        self.global_menu_handler.insert("Save all",
                                        parent=g_art,
                                        callback=self.global_menu_save_all_cb)
        self.global_menu_handler.insert("Reload",
                                        parent=g_art,
                                        callback=self.global_menu_reload_cb)

        g_det = self.global_menu_handler.insert("Detected")
        self.global_menu_handler.insert("Pause",
                                        parent=g_det,
                                        callback=self.global_menu_pause_cb)
        self.global_menu_handler.insert(
            "Clear all",
            parent=g_det,
            callback=self.global_menu_det_clear_all_cb)

        self.a_obj_menu_handler = MenuHandler()
        mov = self.a_obj_menu_handler.insert("Moveable",
                                             callback=self.menu_moveable_cb)
        self.a_obj_menu_handler.setCheckState(mov, MenuHandler.UNCHECKED)
        sc = self.a_obj_menu_handler.insert("Scaleable",
                                            callback=self.menu_scaleable_cb)
        self.a_obj_menu_handler.setCheckState(sc, MenuHandler.UNCHECKED)
        self.a_obj_menu_handler.insert("Save", callback=self.menu_save_cb)
        self.a_obj_menu_handler.insert("Clear", callback=self.menu_remove_cb)

        self.d_obj_menu_handler = MenuHandler()
        self.d_obj_menu_handler.insert("Clear", callback=self.d_menu_clear_cb)

        int_marker = InteractiveMarker()
        int_marker.header.frame_id = self.world_frame
        int_marker.pose.position.z = 1.2
        int_marker.scale = 0.5
        int_marker.name = "global_menu"
        int_marker.description = "Global Menu"
        control = InteractiveMarkerControl()

        control.interaction_mode = InteractiveMarkerControl.BUTTON
        control.always_visible = True

        marker = Marker()

        marker.type = Marker.CUBE
        marker.scale.x = 0.05
        marker.scale.y = 0.05
        marker.scale.z = 0.05
        marker.color.r = 0.5
        marker.color.g = 0.5
        marker.color.b = 0.5
        marker.color.a = 0.5

        control.markers.append(marker)
        int_marker.controls.append(control)

        self.im_server.insert(int_marker, self.ignored_cb)
        self.global_menu_handler.apply(self.im_server, int_marker.name)
        self.im_server.applyChanges()

    def ignored_cb(self, feedback):

        pass

    def d_menu_clear_cb(self, f):

        pass

    def global_menu_det_clear_all_cb(self, f):

        for name in self.clear_all_det():

            self.im_server.erase(name)

        self.im_server.applyChanges()

    def global_menu_pause_cb(self, f):

        handle = f.menu_entry_id
        state = self.global_menu_handler.getCheckState(handle)

        if state == MenuHandler.CHECKED:

            self.global_menu_handler.setCheckState(handle,
                                                   MenuHandler.UNCHECKED)
            self.paused = False

        else:

            self.global_menu_handler.setCheckState(handle, MenuHandler.CHECKED)
            self.paused = True

        self.global_menu_handler.reApply(self.im_server)
        self.im_server.applyChanges()

    def global_menu_save_all_cb(self, f):

        self.save_primitives()

    def global_menu_add_prim_cb(self, feedback):

        p = CollisionPrimitive()
        p.name = self._generate_name()
        p.bbox.type = SolidPrimitive.BOX
        p.bbox.dimensions = [0.1, 0.1, 0.1]
        p.pose.header.frame_id = self.world_frame
        p.pose.pose.orientation.w = 1
        p.pose.pose.position.z = 0.5
        p.setup = self.setup

        self.add_primitive(p)

    def global_menu_reload_cb(self, feedback):

        self.reload()

    def global_menu_clear_all_cb(self, feedback):

        self.clear_all(permanent=False)

    def global_menu_clear_all_perm_cb(self, feedback):

        self.clear_all()

    def menu_save_cb(self, f):

        self.save_primitive(f.marker_name)

    def menu_scaleable_cb(self, f):

        handle = f.menu_entry_id
        state = self.a_obj_menu_handler.getCheckState(handle)

        if state == MenuHandler.CHECKED:

            self.a_obj_menu_handler.setCheckState(handle,
                                                  MenuHandler.UNCHECKED)
            # TODO

        else:

            self.a_obj_menu_handler.setCheckState(handle, MenuHandler.CHECKED)
            # TODO

        self.a_obj_menu_handler.reApply(self.im_server)
        self.im_server.applyChanges()

    def menu_moveable_cb(self, feedback):

        handle = feedback.menu_entry_id
        state = self.a_obj_menu_handler.getCheckState(handle)

        if state == MenuHandler.CHECKED:

            self.a_obj_menu_handler.setCheckState(handle,
                                                  MenuHandler.UNCHECKED)
            # if feedback.marker_name in self.moveable:
            #    self.moveable.remove(feedback.marker_name)

            self.im_server.erase(feedback.marker_name)
            self.im_server.insert(
                make_def(self.artificial_objects[feedback.marker_name]),
                self.process_im_feedback)

        else:

            self.a_obj_menu_handler.setCheckState(handle, MenuHandler.CHECKED)
            self.make_interactive(
                self.artificial_objects[feedback.marker_name])

        self.a_obj_menu_handler.reApply(self.im_server)
        self.im_server.applyChanges()

    def menu_remove_cb(self, feedback):

        self.remove_name(feedback.marker_name)

    def process_im_feedback(self, feedback):

        if feedback.event_type == InteractiveMarkerFeedback.POSE_UPDATE:

            ps = PoseStamped()
            ps.header = feedback.header
            ps.pose = feedback.pose

            if feedback.marker_name in self.artificial_objects:

                self.set_primitive_pose(feedback.marker_name, ps)

            elif feedback.marker_name:

                # detected objects
                pass

    def make_interactive(self, p):

        im = self.im_server.get(p.name)

        for v in (("x", (1, 0, 0, 1)), ("y", (0, 0, 1, 1)), ("z", (0, 1, 0,
                                                                   1))):
            im.controls.append(rotate_axis_control("rotate_" + v[0], v[1]))
            im.controls.append(move_axis_control("move_" + v[0], v[1]))

    def remove_name(self, name):

        super(IntCollisionEnv, self).remove_name(name)

        self.im_server.erase(name)
        self.im_server.applyChanges()

    def add_primitive(self, p):

        super(IntCollisionEnv, self).add_primitive(p)

        self.im_server.insert(make_def(p), self.process_im_feedback)
        self.a_obj_menu_handler.apply(self.im_server, p.name)
        self.im_server.applyChanges()

    def reload(self):

        self.im_server.clear()
        self.create_menus()
        super(IntCollisionEnv, self).reload()

    def add_detected(self, name, ps, object_type):

        super(IntCollisionEnv, self).add_detected(name, ps, object_type)

        p = CollisionPrimitive()
        p.name = name
        p.pose = ps
        p.bbox = object_type.bbox

        self.im_server.insert(make_def(p, color=(0, 0, 1)),
                              self.process_im_feedback)
        self.im_server.applyChanges()

    def clear_detected(self, name):

        super(IntCollisionEnv, self).clear_detected(name)
        self.im_server.erase(name)
        self.im_server.applyChanges()

    def check_attached_timer_cb(self, evt):

        for name, ps, bbox in self.get_attached():

            p = CollisionPrimitive()
            p.name = name
            p.pose = ps
            p.bbox = bbox

            self.im_server.insert(make_def(p, color=(1, 0, 0)),
                                  self.process_im_feedback)
            self.im_server.applyChanges()