int main(int argc, char** argv) { // ros initialization ros::init(argc, argv, "dvrk_mtm_logic"); ros::NodeHandle nh; ros::Rate rate(200); // 100 hz rate // subscriber ros::Subscriber sub_mtm_cmd = nh.subscribe("/dvrk_mtm/cartesian_pose_command", 1, mtm_cmd_pose_cb); ros::Subscriber sub_mtm_fb = nh.subscribe("/dvrk_mtm/joint_states", 1, mtm_joint_feedback_cb); ros::Subscriber sub_mode = nh.subscribe("/dvrk_mtm/control_mode", 1, mtm_mode_cb); // publisher ros::Publisher pub_mtm_joint_state = nh.advertise<sensor_msgs::JointState>("/dvrk_mtm/joint_states_command", 1); ros::Publisher pub_mtm_pose = nh.advertise<geometry_msgs::PoseStamped>("/dvrk_mtm/cartesian_pose_current", 1); ros::Publisher pub_mtm_enable_slider = nh.advertise<sensor_msgs::JointState>("/dvrk_mtm/joint_state_publisher/enable_slider", 100); // cisst robManipulator std::string filename = ros::package::getPath("dvrk_kinematics"); filename.append("/config/dvmtm.rob"); robManipulator mtm_manip; robManipulator::Errno result; result = mtm_manip.LoadRobot(filename); if (result == robManipulator::EFAILURE) { ROS_ERROR("failed to load manipulator config file: %s", filename.c_str()); } else { ROS_INFO("loaded psm manipulator"); } // initialize joint current/command/msg_js mtm_joint_current.SetSize(7); // 7 joints mtm_joint_current.SetAll(0.0); mtm_joint_command.ForceAssign(mtm_joint_current); sensor_msgs::JointState msg_full_js; msg_full_js.name.clear(); msg_full_js.name.push_back("right_outer_yaw_joint"); msg_full_js.name.push_back("right_shoulder_pitch_joint"); msg_full_js.name.push_back("right_elbow_pitch_joint"); msg_full_js.name.push_back("right_wrist_platform_joint"); msg_full_js.name.push_back("right_wrist_pitch_joint"); msg_full_js.name.push_back("right_wrist_yaw_joint"); msg_full_js.name.push_back("right_wrist_roll_joint"); geometry_msgs::PoseStamped msg_pose; int counter = 0; // ------------ run() -------------------------- while (ros::ok()) { // --------- Compute current pose & publish ---------- // psm forward kinematics mtm_pose_current = mtm_manip.ForwardKinematics(mtm_joint_current); mtsCISSTToROS(mtm_pose_current, msg_pose); // if (count % 10 == 0) { // std::cerr << mtm_pose_current << std::endl << std::endl; // } // publish current pose pub_mtm_pose.publish(msg_pose); // MODE_RESET: send HOME joint position // MODE_MANUAL: controled by JSP GUI, not sending anything to jsp // MODE_HOLD: disable JSP GUI, not sending anything to jsp // MODE_CLUTCH: enable J1-3 slider, J4-7 follow // MODE_TELEOP: take command pose, send to jsp // ----- control mode ------- switch (control_mode) { case MTM::MODE_RESET: mtm_joint_command.SetAll(0.0); mtm_joint_command[3] = cmnPI_2; mtm_joint_command[4] = cmnPI_2; break; case MTM::MODE_MANUAL: mtm_joint_command.ForceAssign(mtm_joint_current); std::fill(msg_full_js.position.begin(), msg_full_js.position.end(), 1); pub_mtm_enable_slider.publish(msg_full_js); break; case MTM::MODE_HOLD: mtm_joint_command.ForceAssign(mtm_joint_current); std::fill(msg_full_js.position.begin(), msg_full_js.position.end(), -1); pub_mtm_enable_slider.publish(msg_full_js); break; case MTM::MODE_CLUTCH: mtm_joint_command.ForceAssign(mtm_joint_current); std::fill(msg_full_js.position.begin(), msg_full_js.position.begin()+3, 1); std::fill(msg_full_js.position.begin()+3, msg_full_js.position.end(), -1); pub_mtm_enable_slider.publish(msg_full_js); break; case MTM::MODE_TELEOP: // teleop std::fill(msg_full_js.position.begin(), msg_full_js.position.end(), 1); pub_mtm_enable_slider.publish(msg_full_js); break; default: break; } // copy to msg msg_full_js.position.resize(mtm_joint_command.size()); std::copy(mtm_joint_command.begin(), mtm_joint_command.end(), msg_full_js.position.begin()); if (control_mode == MTM::MODE_RESET) { // publish cmd joint state pub_mtm_joint_state.publish(msg_full_js); } // MODE_HOLE && MODE_CLUTCH if (control_mode == MTM::MODE_HOLD || control_mode == MTM::MODE_CLUTCH) { // inverse kinematics mtm_joint_command.ForceAssign(mtm_joint_current); mtm_manip.InverseKinematics(mtm_joint_command, mtm_pose_command); // now copy to msg_rot_js rotation only sensor_msgs::JointState msg_rot_js; msg_rot_js.name.clear(); msg_rot_js.name.push_back("right_wrist_platform_joint"); msg_rot_js.name.push_back("right_wrist_pitch_joint"); msg_rot_js.name.push_back("right_wrist_yaw_joint"); msg_rot_js.name.push_back("right_wrist_roll_joint"); msg_rot_js.position.resize(4); // only last 4 joints std::copy(mtm_joint_command.begin()+3, mtm_joint_command.end(), msg_rot_js.position.begin()); pub_mtm_joint_state.publish(msg_rot_js); } ros::spinOnce(); rate.sleep(); counter++; } return 0; }
void mtsTeleop::Run(void) { // increment counter counter_++; // cisst process queued commands ProcessQueuedCommands(); // refresh data ros::spinOnce(); // publish #if 1 if (counter_%10 == 0) { // std::cerr << "clutch = " << is_clutch_pressed_ << std::endl; // std::cerr << " mtm = " << std::endl // << mtm_pose_cur_ << std::endl; } #endif vctMatRot3 mtm2psm; mtm2psm.Assign(-1.0, 0.0, 0.0, 0.0, -1.0, 0.0, 0.0, 0.0, 1.0); vctMatRot3 mtm02psm0; mtm02psm0.Assign(1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, -1.0, 0.0); vctMatRot3 psm6tomtm7; psm6tomtm7.Assign(1.0, 0.0, 0.0, 0.0, 0.0, -1.0, 0.0, 1.0, 0.0); if (is_enabled_) { // assign current psm pose psm_pose_cmd_.Assign(psm_pose_cur_); // translation double scale = 0.2; vct3 mtm_tra = mtm_pose_cur_.Translation() - mtm_pose_pre_.Translation(); vct3 psm_tra = scale * mtm_tra; psm_pose_cmd_.Translation() = psm_pose_cmd_.Translation() + mtm2psm * psm_tra; // rotation vctMatRot3 psm_motion_rot; //psm_motion_rot = mtm2psm * mtm_pose_cur_.Rotation() * psm6tomtm7; psm_motion_rot = mtm02psm0* mtm_pose_cur_.Rotation() * psm6tomtm7; psm_pose_cmd_.Rotation().FromNormalized(psm_motion_rot); // std::cerr << " teleop enabled " << counter_ << std::endl; } else { // In this mode, MTM orientation follows PSM orientation // keep current pose psm_pose_cmd_.Assign(psm_pose_cur_); // mtm needs to follow psm orientation mtm_pose_cmd_.Assign(mtm_pose_cur_); vctMatRot3 mtm_rot_cmd; mtm_rot_cmd = mtm02psm0.Inverse() * psm_pose_cur_.Rotation() * psm6tomtm7.Inverse(); mtm_pose_cmd_.Rotation().FromNormalized(mtm_rot_cmd); } mtsCISSTToROS(psm_pose_cmd_, msg_psm_pose_); pub_psm_pose_.publish(msg_psm_pose_); mtsCISSTToROS(mtm_pose_cmd_, msg_mtm_pose_); pub_mtm_pose_.publish(msg_mtm_pose_); // save current pose as previous mtm_pose_pre_.Assign(mtm_pose_cur_); #if 0 if (counter_%10 == 0) { std::cerr << " mtm = " << std::endl << mtm_pose_cur_ << std::endl; std::cerr << "psm = " << std::endl << psm_pose_cur_ << std::endl << std::endl; } #endif }