SLAM 导航小车的持续研究

     1532620977586210.png

    对于智能硬件的研究,在2014年的时候就开始投入了,也不知道是为啥,无论为了前景还是兴趣,作为前端工程师的我,好像跟这个硬件关系不大,纯粹就是觉得好玩。对那些比如四轴飞机,固定翼飞机,机器人等等非常好奇,好奇他们是怎么做到的,可能对于机械自动化专业的人觉得挺简单的,我自己也开始折腾的生涯。

     对于网上一大把的智能小车,手机蓝牙控制的,几年前已经玩过了,手机控制小车,51单片机,蓝牙模块与用过了,觉得51单片机太难入门,于是换成了树莓派。

     之后参加了一场黑客马拉松,认识了一些懂硬件的小伙伴,认识了arduino,于是把arduino和树莓派都装到了小车上。

     后来有一段时间迷上了固定翼飞机(FPV),买了一个遥控器和电池回来,后来一个电机,装上。有一次电机失控,螺旋桨直接飞了出来,幸好当时没人在附近,但是由于太危险了,就放弃玩这个了。

     后来发现,蓝牙控制小车距离太短,而且感觉有点low,于是我把买给飞机用的遥控器和电池组都移植到了小车上,这样我的遥控车就有了超长距离的遥控(几公里吧),和十足的动力(900元的4S电池)。

     有了超远距离的实时控制还不够,其实我还需要想,能不能在公司,就能控制家里的小车,这其实是一件非常非常难的事情。wifi是有延迟的,稍微一点的网络延迟几百毫秒,车子就撞墙了,信号就丢了,再加上上面有实时摄像头图像传输,那一定会更加慢了。这都是经过我实际躺坑总结出来的经验。

     于是乎,我在想,与其实时控制,那还不如实时定位。先画出一副家里的地图,鼠标点到哪里,车子就自动走到哪里,像玩梦幻西游,点击NPC就会自动走路过去的效果。于是乎。。。这里涉及到的问题,太多太深奥了。

      第一步,要先画出一副家里的地图(这就是这篇文章要探讨内容)

      第二步,让机器识别当前位置是在地图的哪一个位置

      第三步,鼠标点一下地图,用算法自动导航到指定坐标。

      第四步,没电了,是不是应该会自动充电?

      第五步,是不是能够自动跟随某个东西,比如人,宠物?

      第六步,是不是给它整一个机械臂,做一些简单的拿拖鞋之类的事情?

      哈哈,太多了,其中设计到的硬件知识,电子知识,机械知识,软件知识,图像处理,人工智能。而且。。还要花很多钱买设备。以后的事情以后再考虑吧。眼前我只能先踏出第一步。

      好了,故事说到这里,下面是干货。

    

      建立地图。可以理解为,自己做一个拥有导航功能的扫地机器人。

      硬件准备:

            1. 一台智能小车,假设你已经对它非常熟悉。

            2. rpladir A1 激光测距摄像头(2016年买的,这东西我花了900大洋,现在有更贵的版本了)

            3. 树莓派3, 如果有nvidia tx2就更好啦

            4. 台式机Ubuntu系统

      软件环境:

            1.ubuntu 安装ros,这里使用的是ubuntu14  可参考这里安装 http://wiki.ros.org/cn/indigo/Installation

            2.树莓派 安装ros 可参考这里安装  http://wiki.ros.org/ROSberryPi/Installing%20ROS%20Indigo%20on%20Raspberry%20Pi

       

步骤一

因为要测试使用hector,所以我们第一步先安装hector_slam

命令:

sudo apt-get install ros-indigo-hector-slam

步骤二

打包好的文件:https://github.com/ROSClub/rplidar_ros

下载编译rplidar a2的驱动

下载地址:https://github.com/robopeak/rplidar_ros

使用以下命令开始

cd ~/catkin_ws git clone https://github.com/robopeak/rplidar_ros.git cd ~/catkin_ws catkin_make

步骤三:测试雷达

roslaunch rplidar_ros view_rplidar.launch

183107vz5hho5byl1z7l11.png

运行到这一步已经可以说是 雷达收集到数据了,接下来结合hector实现SLAM

步骤三:添加hector_rplidar.launch

rplidar_ros/launch下新建hector_rplidar.launch,并且输入以下内容:

<launch>
  <node pkg="hector_mapping" type="hector_mapping" name="hector_mapping" output="screen">
    <!-- Frame names -->
    <param name="pub_map_odom_transform" value="true"/>
    <param name="map_frame" value="map" />
    <param name="base_frame" value="base_link" />
    <param name="odom_frame" value="base_link" />

    <!-- Tf use -->
    <param name="use_tf_scan_transformation" value="true"/>
    <param name="use_tf_pose_start_estimate" value="false"/>

    <!-- Map size / start point -->
    <param name="map_resolution" value="0.05"/>
    <param name="map_size" value="2048"/>
    <param name="map_start_x" value="0.5"/>
    <param name="map_start_y" value="0.5" />
    <param name="laser_z_min_value" value = "-1.0" />
    <param name="laser_z_max_value" value = "1.0" />
    <param name="map_multi_res_levels" value="2" />

    <param name="map_pub_period" value="2" />
    <param name="laser_min_dist" value="0.4" />
    <param name="laser_max_dist" value="5.5" />
    <param name="output_timing" value="false" />
    <param name="pub_map_scanmatch_transform" value="true" />
    <!--<param name="tf_map_scanmatch_transform_frame_name" value="scanmatcher_frame" />-->

    <!-- Map update parameters -->
    <param name="update_factor_free" value="0.4"/>
    <param name="update_factor_occupied" value="0.7" />
    <param name="map_update_distance_thresh" value="0.2"/>
    <param name="map_update_angle_thresh" value="0.06" />

    <!-- Advertising config -->
    <param name="advertise_map_service" value="true"/>
    <param name="scan_subscriber_queue_size" value="5"/>
    <param name="scan_topic" value="scan"/>
  </node>

  <node pkg="rplidar_ros" type="rplidarNode" name="rplidarNode" output="screen">
    <param name="serial_port"         type="string" value="/dev/ttyUSB0"/>
    <param name="serial_baudrate"     type="int"    value="115200"/>
    <param name="frame_id"            type="string" value="laser"/>
    <param name="inverted"            type="bool"   value="false"/>
    <param name="angle_compensate"    type="bool"   value="true"/>
  </node>

  <node pkg="tf" type="static_transform_publisher" name="base_to_laser_broadcaster" args="0 0 0 0 0 0 /base_link /laser 100"/>
  <node pkg="rviz" type="rviz" name="rviz" args="-d $(rplidar_ros)/rviz/mapping_demo.rviz"/>

</launch>

编译一下

cd ~/catkin_ws catkin_make

运行测试:

roslaunch rplidar_ros hector_mapping_demo.launch

1532619231295707.png

这时候ROS已经是可以绘图了,但是激光雷达是插在ubuntu主机上面的,并不能移动。需要把激光雷达放在小车地盘上,ubuntu作为数据处理和展示,树莓派作为数据收集,这时候需要用到ROS分布式的操作。

因为ros是可以分布式运行的,以前参考了过一个乌龟控制的教程 turtlesim    https://blog.csdn.net/heyijia0327/article/details/42080641

利用这个原理,把分布式的环境搭建好。

TK1 IP:192.168.1.100

笔记本IP:192.168.1.101

配置好主从机操作:

tk1操作:bashrc文件下设置主机的IP

vim ~/.bashrc

最后添加: export ROS_MASTER_URI=http://193.168.1.101:11311

我的工作空间:

cd ~/mrobot/src
git clone https://github.com/ROSClub/rplidar_ros
cd ~/mrobot
catkin_make
roslaunch rplidar_ros hector_rplidar.launch

控制小车移动,即可绘出地图

1532619974593326.png

评论关闭。