ROS 教程之navigation: 用程序设定导航目标点
?? ? ? 在做導(dǎo)航的過程中,目的地都是通過RViz界面手動(dòng)設(shè)置的,很麻煩。那么能否通過程序設(shè)置目標(biāo)點(diǎn),讓機(jī)器人自動(dòng)在幾個(gè)目標(biāo)點(diǎn)之間來回循環(huán)呢?答案是肯定的,《Ros by Example volumn1》8.5.3節(jié)中也給出了答案。但是,本文給出一個(gè)更簡單的例子,在機(jī)器人前方1m處設(shè)定目標(biāo)點(diǎn),文章內(nèi)容幾乎來自ROS navigation 官方wiki文檔。
? ? ? ?在進(jìn)行下面的試驗(yàn)之前,希望你已經(jīng)在自己的機(jī)器人上完成了使用move_base進(jìn)行控制的任務(wù)。
? ? ? ?第一步:創(chuàng)建用于發(fā)布目標(biāo)點(diǎn)的package,包名稱為simple_navigation_goals:
$ catkin_create_pkg simple_navigation_goals move_base_msgs actionlib roscpp 如果你不想創(chuàng)建一個(gè)包,而是在已有的package下創(chuàng)建一個(gè)節(jié)點(diǎn),那必須修改這個(gè)package的package.xml文件:
在相應(yīng)位置處添加上如下幾行:
<bulid_depend>move_base_msgs</bulid_depend> <bulid_depend>actionlib</bulid_depend>以及:
<run_depend>move_base_msgs</run_depend> <run_depend>actionlib</run_depend> ? ? ? ? 第二步:在這個(gè)package下的src文件下用文本編輯器創(chuàng)建一個(gè)cpp文件send_goal.cpp。如果還沒有src文件夾,自己手動(dòng)創(chuàng)建一個(gè)。將下列代碼復(fù)制進(jìn)去: #include <ros/ros.h> #include <move_base_msgs/MoveBaseAction.h> #include <actionlib/client/simple_action_client.h>typedef actionlib::SimpleActionClient<move_base_msgs::MoveBaseAction> MoveBaseClient;int main(int argc, char** argv){ros::init(argc, argv, "simple_navigation_goals");//tell the action client that we want to spin a thread by defaultMoveBaseClient ac("move_base", true);//wait for the action server to come upwhile(!ac.waitForServer(ros::Duration(5.0))){ROS_INFO("Waiting for the move_base action server to come up");}move_base_msgs::MoveBaseGoal goal;//we'll send a goal to the robot to move 1 meter forwardgoal.target_pose.header.frame_id = "base_link";goal.target_pose.header.stamp = ros::Time::now();goal.target_pose.pose.position.x = 1.0;goal.target_pose.pose.orientation.w = 1.0;ROS_INFO("Sending goal");ac.sendGoal(goal);ac.waitForResult();if(ac.getState() == actionlib::SimpleClientGoalState::SUCCEEDED)ROS_INFO("Hooray, the base moved 1 meter forward");elseROS_INFO("The base failed to move forward 1 meter for some reason");return 0; } 代碼解讀:
? ? 1. 注意代碼中用的是action,不是服務(wù)service。ROS中的服務(wù)service是一問一答的形式,你來查詢了,我就返給你要的信息。action也有服務(wù)的概念,但是它不一樣的地方是不是一問一答,而多了一個(gè)反饋,它會(huì)不斷反饋項(xiàng)目進(jìn)度。如這里,你設(shè)定了目標(biāo)點(diǎn),反饋信息可能是機(jī)器人在規(guī)劃路徑上的即時(shí)位姿,直到機(jī)器人到達(dá)目標(biāo)點(diǎn),返回SUCCEEDED消息。有關(guān)actionlib的具體知識(shí)請參加ROS官方wiki。
? ? 2.這段程序的目的是是移動(dòng)機(jī)器人前進(jìn)1m。注意程序中:
這里設(shè)定目標(biāo)點(diǎn)goal所在的坐標(biāo)系base_link,因此目標(biāo)點(diǎn)位姿position.x = 1 的含義是在當(dāng)前base_link中前進(jìn)1m。當(dāng)然你可將目標(biāo)點(diǎn)設(shè)定在絕對坐標(biāo)系中,如在map坐標(biāo)系。至于在map坐標(biāo)系中,具體的目標(biāo)點(diǎn)參數(shù)如何得到?可以使用RViz中的navigation goal,點(diǎn)擊地圖中相應(yīng)點(diǎn)進(jìn)行查看。
? ? ? 第三步:編譯并運(yùn)行
? ? ? 要使得上述程序會(huì)生成可執(zhí)行文件,還需要對package的CMakeList.txt文件進(jìn)行修改:
add_executable(send_goal src/send_goal.cpp) target_link_libraries(send_goal ${catkin_LIBRARIES}) 接下來可以編譯了: $ cd ~/catkin_ws $ catkin_make
? ? ? ?運(yùn)行:
? ? ? ?注意,如果你程序中使用的是map坐標(biāo)系,和定位導(dǎo)航一樣,應(yīng)該在RViz中設(shè)定機(jī)器人初始位姿以后,才開始執(zhí)行這個(gè)發(fā)送目標(biāo)點(diǎn)的節(jié)點(diǎn),這樣做的目的是滿足機(jī)器人的定位要求,使得amcl包能正確運(yùn)行。如果是base_link坐標(biāo)系則關(guān)系不大,因?yàn)槟繕?biāo)點(diǎn)是相對機(jī)器人的,運(yùn)行程序以后,你將看到機(jī)器人前進(jìn)1m。
? ? ??
? ??
(轉(zhuǎn)載請注明作者和出處:http://blog.csdn.net/heyijia0327?未經(jīng)允許請勿用于商業(yè)用途)
總結(jié)
以上是生活随笔為你收集整理的ROS 教程之navigation: 用程序设定导航目标点的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: npm 升级所有依赖包
- 下一篇: 手工焊锡通用工艺规程