上一节写了用键盘控制节点控制仿真小车运动,这一节需要配置小车的里程计,并且在room_mini这个world中进行gmapping建图。
1.配置小车里程计 通过gazebo节点获取odom从/gazebo/link_states话题中读取gazebo_msgs/LinKStates消息,再从msg.name.index中提取racebot::base_footprint位姿数据,将数据整理打包发布为里程计信息,在racebot_control/scripts中新建文件gazebo_odometry.py,代码如下:
#!/usr/bin/env python
'''
This script makes Gazebo less fail by translating gazebo status messages to odometry data.
Since Gazebo also publishes data faster than normal odom data, this script caps the update to 20hz.
Winter Guerra
'''
import rospy
from nav_msgs.msg import Odometry
from geometry_msgs.msg import Pose, Twist, Transform, TransformStamped
from gazebo_msgs.msg import LinkStates
from std_msgs.msg import Header
import numpy as np
import math
import tf2_ros
class OdometryNode:
# Set publishers
pub_odom = rospy.Publisher('/odom', Odometry, queue_size=1)
def __init__(self):
# init internals
self.last_received_pose = Pose()
self.last_received_twist = Twist()
self.last_recieved_stamp = None
# Set the update rate
rospy.Timer(rospy.Duration(.05), self.timer_callback) # 20hz
self.tf_pub = tf2_ros.TransformBroadcaster()
# Set subscribers
rospy.Subscriber('/gazebo/link_states', LinkStates, self.sub_robot_pose_update)
def sub_robot_pose_update(self, msg):
# Find the index of the racecar
try:
arrayIndex = msg.name.index('racebot::base_footprint')
except ValueError as e:
# Wait for Gazebo to startup
pass
else:
# Extract our current position information
self.last_received_pose = msg.pose[arrayIndex]
self.last_received_twist = msg.twist[arrayIndex]
self.last_recieved_stamp = rospy.Time.now()
def timer_callback(self, event):
if self.last_recieved_stamp is None:
return
cmd = Odometry()
cmd.header.stamp = self.last_recieved_stamp
cmd.header.frame_id = 'odom'
cmd.child_frame_id = 'base_footprint'
cmd.pose.pose = self.last_received_pose
cmd.twist.twist = self.last_received_twist
cmd.pose.covariance =[1e-3, 0, 0, 0, 0, 0,
0, 1e-3, 0, 0, 0, 0,
0, 0, 1e6, 0, 0, 0,
0, 0, 0, 1e6, 0, 0,
0, 0, 0, 0, 1e6, 0,
0, 0, 0, 0, 0, 1e3]
cmd.twist.covariance = [1e-9, 0, 0, 0, 0, 0,
0, 1e-3, 1e-9, 0, 0, 0,
0, 0, 1e6, 0, 0, 0,
0, 0, 0, 1e6, 0, 0,
0, 0, 0, 0, 1e6, 0,
0, 0, 0, 0, 0, 1e-9]
self.pub_odom.publish(cmd)
tf = TransformStamped(
header=Header(
frame_id=cmd.header.frame_id,
stamp=cmd.header.stamp
),
child_frame_id=cmd.child_frame_id,
transform=Transform(
translation=cmd.pose.pose.position,
rotation=cmd.pose.pose.orientation
)
)
self.tf_pub.sendTransform(tf)
# Start the node
if __name__ == '__main__':
rospy.init_node("gazebo_odometry_node")
node = OdometryNode()
rospy.spin()
修改racebot_control.launch,将里程计发布节点添加进去:
2.令小车在房间内gmapping建图
在配置好里程计和控制节点后,可以开始建图gmapping了,先安装gmapping功能包:
sudo apt-get install ros-melodic-gmapping
在racebot/launch文件夹中创建slam_gmapping.launch:
运行一下,并打开rviz进行配置,添加雷达,添加map,添加小车模型:
roslaunch racebot_gazebo racebot.launch
roslaunch racebot_gazebo slam_gmapping.launch
rviz
用键盘控制小车在房间内跑动建图,建好图后保存:
rosrun map_server map_saver -f room_mini
将保存的地图置于racebot_gazebo/map路径下边。并将rviz设置保存于racebot_gazebo/rviz路径,并命名为gmapping.rviz,新建gmapping.launch,下一次gmapping的时候可以不用进行设置:
小结
本节内容配置小车里程计,并用gmapping让小车在房间中建立了房间的二维栅格地图,下一节用amcl定位以及teb本地规划器让小车在房间里面进行导航。
参考资料1.古月老师的<
2.古月学院《如何在Gazebo中实现阿克曼转向车的仿真 • 王泽恩》
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)