机器人系统仿真

0、何为仿真

  • 通过计算机对实体机器人系统进行模拟的技术。

 
 

1、为何仿真

  • 低成本: 机器人实体一般价格昂贵,为降低机器人学习、调试的成本;
  • 高效: 搭建的环境更为多样且灵活,可以提高测试效率以及测试覆盖率;
  • 高安全性: 仿真环境下,无需要考虑耗损问题。

 
 

2、仿真技术的内容与要求

 
 

2.0、介绍创建ros包的流程。

  1. 创建工作空间

  2. 创建Ros包

  3. 编写源码

  4. 编译

  5. 运行包

 

2.0.1 创建工作空间【并初始化】


mkdir -p catkin_ws/src                       // 若创建嵌套文件夹,必须使用 -p,创建单个文件夹则不用

cd catkin_ws                                           // 进入该工作空间

catkin_make                                           // 初始化工作空间

 

2.0.2 创建Ros包【使用依赖】


cd src													// 进入工作空间的src内

catkin_create_pkg ros_test roscpp rospy std_msgs

 

2.0.3 编写源码


cd catkin_ws/src/ros_test/src

编写 src 内的源码文件 ***.cpp


cd catkin_ws/src/ros_test

改写 ros_test 内的 CMakeLists.txt 文件

 

2.0.4 编译Ros包


cd catkin_ws

catkin_make

 

2.0.5 运行Ros包


// 新开终端,执行
roscore

//另一终端执行
ca catkin_ws
source devel/setup.bash
rosrun ros_test ros_test_node				// rusrun 包名 节点名

 

 

3、 URDF

URDF是 Unified Robot Description Format 的首字母缩写,直译为 统一(标准化)机器人描述格式 ,可以以一种 XML 的方式描述机器人的部分结构,比如底盘、摄像头、激光雷达、机械臂以及不同关节的自由度…,该文件可以被 C++ 内置的解释器转换成可视化的机器人模型,是 ROS 中实现机器人仿真的重要组件。

URDF 不能单独使用,需要结合 Rviz 或 Gazebo,URDF 只是一个文件,需要在 Rviz 或 Gazebo 中渲染成图形化的机器人模型。

 
 

4、 URDF 集成 Rviz 流程

1. 准备: 新建功能包,导入依赖;

  • 创建一个新的功能包,导入依赖 urdf xacro
// 创建工作空间 并 初始化
mkdir -p catkin_ws/src
cd catkin_ws
catkin_make

// 创建功能包 并 导入依赖
cd catkin_ws/src/
catkin_create_pkg ros_test urdf xacro
  • 在当前功能包下,再新建几个目录:
    • urdf:存储urdf文件的目录
    • meshes:存储机器人模型渲染文件
    • config:存储配置文件,比如 **.rviz 文件
    • launch:存储launch启动文件
// 功能包内新建文件夹
cd catkin_ws/src/ros_test
mkdir -p urdf/urdf    // 此为创建均为urdf的两层目录,也可以只创建一层urdf目录【双层是为了之后建urdf/xacro】
mkdir meshes
mkdir config
mkdir launch

2.1 核心: 编写【 urdf 文件】 与 launch 文件

// 创建urdf文件,并填入相应内容
cd catkin_ws/src/ros_test/urdf/urdf
gedit urdf01_HelloWorld.urdf

// 填入如下内容
<robot name="mycar">
    <link name="base_link">
        <visual>
            <geometry>
                <box size="0.5 0.2 0.1" />
            </geometry>
        </visual>
    </link>
</robot>

// 解释urdf文件
一、robot
urdf 中为了保证 xml 语法的完整性,使用了robot标签作为根标签,
所有的 link 和 joint 以及其他标签都必须包含在 robot 标签内,在该标签内可以通过 name 属性设置机器人模型的名称

1.属性
name: 指定机器人模型的名称

2.子标签

其他标签都是子级标签

```cpp

// 解释urdf文件
二、link

urdf 中的 link 标签用于描述机器人某个部件(也即刚体部分)的外观和物理属性,比如: 机器人底座、轮子、激光雷达、摄像头...
          每一个部件都对应一个 link, 在 link 标签内,可以设计该部件的形状、尺寸、颜色、惯性矩阵、碰撞参数等一系列属性

1.属性
    name ---> 为连杆命名

2.子标签
    visual ---> 描述外观(对应的数据是可视的)

        geometry 设置连杆的形状

            标签1: box(盒状)
                属性:size=(x)(y)(z)

            标签2: cylinder(圆柱)
                属性:radius=半径 length=高度

            标签3: sphere(球体)
                属性:radius=半径

            标签4: mesh(为连杆添加皮肤)
                属性: filename=资源路径(格式:package://<packagename>/<path>/文件)

        origin 设置偏移量与倾斜弧度

            属性1: xyz=x偏移 y便宜 z偏移

            属性2: rpy=x翻滚 y俯仰 z偏航 (单位是弧度)

        metrial 设置材料属性(颜色)

            属性: name

            标签: color
                属性: rgba=红绿蓝权重值与透明度 (每个权重值以及透明度取值[0,1])

    collision ---> 连杆的碰撞属性

    Inertial ---> 连杆的惯性矩阵

在此,只演示visual使用。

 

link 案例

需求:分别生成长方体、圆柱与球体的机器人部件

URDF文件示例如下:

    <link name="base_link">
        <visual>
            <!-- 形状 -->
            <geometry>
                <!-- 长方体的长宽高 -->
                <!-- <box size="0.5 0.3 0.1" /> -->
                <!-- 圆柱,半径和长度 -->
                <!-- <cylinder radius="0.5" length="0.1" /> -->
                <!-- 球体,半径-->
                <!-- <sphere radius="0.3" /> -->

            </geometry>
            <!-- xyz坐标 rpy翻滚俯仰与偏航角度(3.14=180度 1.57=90度) -->
            <origin xyz="0 0 0" rpy="0 0 0" />
            <!-- 颜色: r=red g=green b=blue a=alpha -->
            <material name="black">
                <color rgba="0.7 0.5 0 0.5" />
            </material>
        </visual>
    </link>

 
 
在这里插入图片描述

// 解释urdf文件
三、joint

urdf 中的 joint 标签用于描述机器人关节的运动学和动力学属性,还可以指定关节运动的安全极限,机器人的两个部件(分别称之为 parent link 与 child link)"关节"的形式相连接,不同的关节有不同的运动形式: 旋转、滑动、固定、旋转速度、旋转角度限制....,比如:安装在底座上的轮子可以360度旋转,而摄像头则可能是完全固定在底座上。

joint标签对应的数据在模型中是不可见的
1.属性

    name ---> 为关节命名

    type ---> 关节运动形式

        continuous: 旋转关节,可以绕单轴无限旋转

        revolute: 旋转关节,类似于 continues,但是有旋转角度限制

        prismatic: 滑动关节,沿某一轴线移动的关节,有位置极限

        planer: 平面关节,允许在平面正交方向上平移或旋转

        floating: 浮动关节,允许进行平移、旋转运动

        fixed: 固定关节,不允许运动的特殊关节

2.子标签

    parent(必需的)

    parent link的名字是一个强制的属性:
        link:父级连杆的名字,是这个link在机器人结构树中的名字。

    child(必需的)

    child link的名字是一个强制的属性:
        link:子级连杆的名字,是这个link在机器人结构树中的名字。

    origin
        属性: xyz=各轴线上的偏移量 rpy=各轴线上的偏移弧度。

    axis
        属性: xyz用于设置围绕哪个关节轴运动。

 

joint 案例

需求:创建机器人模型,底盘为长方体,在长方体的前面添加一摄像头,摄像头可以沿着 Z 轴 360 度旋转。

URDF文件示例如下:

<!-- 
    需求: 创建机器人模型,底盘为长方体,
         在长方体的前面添加一摄像头,
         摄像头可以沿着 Z 轴 360 度旋转

 -->
<robot name="mycar">
    <!-- 底盘 -->
    <link name="base_link">
        <visual>
            <geometry>
                <box size="0.5 0.2 0.1" />
            </geometry>
            <origin xyz="0 0 0" rpy="0 0 0" />
            <material name="blue">
                <color rgba="0 0 1.0 0.5" />
            </material>
        </visual>
    </link>

    <!-- 摄像头 -->
    <link name="camera">
        <visual>
            <geometry>
                <box size="0.02 0.05 0.05" />
            </geometry>
            <origin xyz="0 0 0" rpy="0 0 0" />
            <material name="red">
                <color rgba="1 0 0 0.5" />
            </material>
        </visual>
    </link>

    <!-- 关节 -->
    <joint name="camera2baselink" type="continuous">
        <parent link="base_link"/>
        <child link="camera" />
        <!-- 需要计算两个 link 的物理中心之间的偏移量 -->
        <origin xyz="0.2 0 0.075" rpy="0 0 0" />
        <axis xyz="0 0 1" />
    </joint>

</robot>

2.2 核心: 编写 urdf 与【 launch 文件】

编写launch文件, launch文件示例如下:

cd launch 
gedit 
<launch>

    <param name="robot_description" textfile="$(find urdf_rviz_demo)/urdf/urdf/urdf03_joint.urdf" />
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf_rviz_demo)/config/helloworld.rviz" /> 

    <!-- 添加关节状态发布节点 -->
    <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" />
    <!-- 添加机器人状态发布节点 -->
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" />
    <!-- 可选:用于控制关节运动的节点 -->
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" />

</launch>

 
 

3. 核心: 在launch文件集成URDF与Rviz;

  • 在 launch 目录下,新建一个launch文件,该 launch 文件需要启动 Rviz,并导入 urdf 文件【此处的包名应为 ros_test】,Rviz 启动后可以自动载入解析urdf文件,并显示机器人模型,核心问题:如何导入 urdf 文件? 在 ROS 中,可以将 urdf 文件的路径设置到参数服务器,使用的参数名是:robot_description,示例代码如下:
cd catkin_ws/src/ros_test/launch
gedit urdf01_HelloWorld.launch
// 填入如下内容
<launch>

    <!-- 设置参数 -->
    <param name="robot_description" textfile="$(find 包名)/urdf/urdf/urdf01_HelloWorld.urdf" />

    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" />

</launch>

 
 

4. 1 显示: 在Rviz中显示机器人模型。

roslaunch ros_test urdf01_HelloWorld.launch
  • rviz 启动后,会发现并没有盒装的机器人模型,这是因为默认情况下没有添加机器人显示组件,需要手动添加,添加方式如下:
    在这里插入图片描述
    在这里插入图片描述
    设置完毕后,可以正常显示了
     
     

4. 2.优化 rviz 启动

  • 重复启动launch文件时,Rviz 之前的组件配置信息不会自动保存,需要重复执行步骤4的操作,为了方便使用,可以使用如下方式优化:

  • 首先,将当前配置保存进config目录

// 在当前路径下:
catkin_ws/src/ros_test/config/
// 保存rivz配置文件
show_mycar.rviz

在这里插入图片描述 

  • 然后,urdf01_HelloWorld.launch文件中 Rviz 的启动配置添加参数:args,值设置为-d 配置文件路径
<launch>
    <param name="robot_description" textfile="$(find 包名)/urdf/urdf/urdf01_HelloWorld.urdf" />
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find 报名)/config/rviz/show_mycar.rviz" />
</launch>

  • 最后再启动时,就可以包含之前的组件配置了,使用更方便快捷。

 
 
 

5、 xacro 集成Rviz【单个xacro文件】


// 创建工作空间 并 初始化
mkdir -p catkin_ws/src
cd catkin_ws
catkin_make

// 创建ros功能包
cd catkin_ws/src
catkin_create_pkg demo_pkg urdf xacro

// 功能包内创建多个文件夹
cd catkin_ws/src/demo_pkg
mkdir -p urdf/xacro
mkdir launch
mkdir config

cd urdf/xacro
gedit my_car.urdf.xacro
// 填入如下内容
<robot name="my_base" xmlns:xacro="http://www.ros.org/wiki/xacro">
    <!---->
    <xacro:property name="PI" value="3.141"/>
    <!--  -->
    <material name="black">
        <color rgba="0.0 0.0 0.0 1.0" />
    </material>
    <!--  -->
    <xacro:property name="base_footprint_radius" value="0.001" /> <!-- base_footprint   -->
    <xacro:property name="base_link_radius" value="0.1" /> <!-- base_link  -->
    <xacro:property name="base_link_length" value="0.08" /> <!-- base_link -->
    <xacro:property name="earth_space" value="0.015" /> <!--  -->

    <!--  -->
    <link name="base_footprint">
      <visual>
        <geometry>
          <sphere radius="${base_footprint_radius}" />
        </geometry>
      </visual>
    </link>

    <link name="base_link">
      <visual>
        <geometry>
          <cylinder radius="${base_link_radius}" length="${base_link_length}" />
        </geometry>
        <origin xyz="0 0 0" rpy="0 0 0" />
        <material name="yellow">
          <color rgba="0.5 0.3 0.0 0.5" />
        </material>
      </visual>
    </link>

    <joint name="base_link2base_footprint" type="fixed">
      <parent link="base_footprint" />
      <child link="base_link" />
      <origin xyz="0 0 ${earth_space + base_link_length / 2 }" />
    </joint>

    <!--  -->
    <!--  -->
    <xacro:property name="wheel_radius" value="0.0325" /><!--  -->
    <xacro:property name="wheel_length" value="0.015" /><!-- -->
    <!--  -->
    <xacro:macro name="add_wheels" params="name flag">
      <link name="${name}_wheel">
        <visual>
          <geometry>
            <cylinder radius="${wheel_radius}" length="${wheel_length}" />
          </geometry>
          <origin xyz="0.0 0.0 0.0" rpy="${PI / 2} 0.0 0.0" />
          <material name="black" />
        </visual>
      </link>

      <joint name="${name}_wheel2base_link" type="continuous">
        <parent link="base_link" />
        <child link="${name}_wheel" />
        <origin xyz="0 ${flag * base_link_radius} ${-(earth_space + base_link_length / 2 - wheel_radius) }" />
        <axis xyz="0 1 0" />
      </joint>
    </xacro:macro>
    <xacro:add_wheels name="left" flag="1" />
    <xacro:add_wheels name="right" flag="-1" />
    <!--  -->
    <!--  -->
    <xacro:property name="support_wheel_radius" value="0.0075" /> <!--  -->

    <!--  -->
    <xacro:macro name="add_support_wheel" params="name flag" >
      <link name="${name}_wheel">
        <visual>
            <geometry>
                <sphere radius="${support_wheel_radius}" />
            </geometry>
            <origin xyz="0 0 0" rpy="0 0 0" />
            <material name="black" />
        </visual>
      </link>

      <joint name="${name}_wheel2base_link" type="continuous">
          <parent link="base_link" />
          <child link="${name}_wheel" />
          <origin xyz="${flag * (base_link_radius - support_wheel_radius)} 0 ${-(base_link_length / 2 + earth_space / 2)}" />
          <axis xyz="1 1 1" />
      </joint>
    </xacro:macro>

    <xacro:add_support_wheel name="front" flag="1" />
    <xacro:add_support_wheel name="back" flag="-1" />

</robot>

cd launch
gedit my_car.launch
// 填入如下内容
<launch>
    <param name="robot_description" command="$(find xacro)/xacro $(find demo64)/urdf/xacro/my_car.urdf.xacro" />

    <node pkg="rviz" type="rviz" name="rviz" />
    <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" output="screen" />
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" output="screen" />
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" output="screen" />
</launch>
// 进入工作空间内进行编译
cd catkin_ws
catkin_make

// 执行权限
source devel/setup.bash

// 启动launch文件
roslaunch demo_pkg my_car.launch

// Rviz启动后,将对Rviz界面进行设置【同上面】,设置好后将其保存进config文件夹内,命名my_car.rviz

// 修改my_car.launch
// 修改如下:指定了Rviz的路径

<launch>
    <param name="robot_description" command="$(find xacro)/xacro $(find demo64)/urdf/xacro/my_car.urdf.xacro"/>

    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find demo64)/config/demo64.rviz"/>
    <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" output="screen" />
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" output="screen" />
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" output="screen" />
</launch>

// 再次启动launch文件
roslaunch demo_pkg my_car.launch

// 会看到模型就在打开的Rviz界面内。

 
 

6、 xacro 集成Rviz【多个xacro文件】


// 创建工作空间 并 初始化
mkdir -p catkin_ws/src
cd catkin_ws
catkin_make

// 创建ros功能包
cd catkin_ws/src
catkin_create_pkg demo_pkg urdf xacro

// 功能包内创建多个文件夹
cd catkin_ws/src/demo_pkg
mkdir -p urdf/xacro
mkdir launch
mkdir config

cd urdf/xacro

// 此处需要创建多个xacro文件

gedit my_car.urdf.xacro

gedit my_camrea.urdf.xacro

gedit my_laser.urdf.xacro

gedit my_car_camera_laser.urdf.xacro
// 分别填入如下内容
<!-- my_car.urdf.xacro -->
<robot name="my_base" xmlns:xacro="http://www.ros.org/wiki/xacro">
    <!---->
    <xacro:property name="PI" value="3.141"/>
    <!--  -->
    <material name="black">
        <color rgba="0.0 0.0 0.0 1.0" />
    </material>
    <!--  -->
    <xacro:property name="base_footprint_radius" value="0.001" /> <!-- base_footprint   -->
    <xacro:property name="base_link_radius" value="0.1" /> <!-- base_link  -->
    <xacro:property name="base_link_length" value="0.08" /> <!-- base_link -->
    <xacro:property name="earth_space" value="0.015" /> <!--  -->

    <!--  -->
    <link name="base_footprint">
      <visual>
        <geometry>
          <sphere radius="${base_footprint_radius}" />
        </geometry>
      </visual>
    </link>

    <link name="base_link">
      <visual>
        <geometry>
          <cylinder radius="${base_link_radius}" length="${base_link_length}" />
        </geometry>
        <origin xyz="0 0 0" rpy="0 0 0" />
        <material name="yellow">
          <color rgba="0.5 0.3 0.0 0.5" />
        </material>
      </visual>
    </link>

    <joint name="base_link2base_footprint" type="fixed">
      <parent link="base_footprint" />
      <child link="base_link" />
      <origin xyz="0 0 ${earth_space + base_link_length / 2 }" />
    </joint>

    <!--  -->
    <!--  -->
    <xacro:property name="wheel_radius" value="0.0325" /><!--  -->
    <xacro:property name="wheel_length" value="0.015" /><!-- -->
    <!--  -->
    <xacro:macro name="add_wheels" params="name flag">
      <link name="${name}_wheel">
        <visual>
          <geometry>
            <cylinder radius="${wheel_radius}" length="${wheel_length}" />
          </geometry>
          <origin xyz="0.0 0.0 0.0" rpy="${PI / 2} 0.0 0.0" />
          <material name="black" />
        </visual>
      </link>

      <joint name="${name}_wheel2base_link" type="continuous">
        <parent link="base_link" />
        <child link="${name}_wheel" />
        <origin xyz="0 ${flag * base_link_radius} ${-(earth_space + base_link_length / 2 - wheel_radius) }" />
        <axis xyz="0 1 0" />
      </joint>
    </xacro:macro>
    <xacro:add_wheels name="left" flag="1" />
    <xacro:add_wheels name="right" flag="-1" />
    <!--  -->
    <!--  -->
    <xacro:property name="support_wheel_radius" value="0.0075" /> <!--  -->

    <!--  -->
    <xacro:macro name="add_support_wheel" params="name flag" >
      <link name="${name}_wheel">
        <visual>
            <geometry>
                <sphere radius="${support_wheel_radius}" />
            </geometry>
            <origin xyz="0 0 0" rpy="0 0 0" />
            <material name="black" />
        </visual>
      </link>

      <joint name="${name}_wheel2base_link" type="continuous">
          <parent link="base_link" />
          <child link="${name}_wheel" />
          <origin xyz="${flag * (base_link_radius - support_wheel_radius)} 0 ${-(base_link_length / 2 + earth_space / 2)}" />
          <axis xyz="1 1 1" />
      </joint>
    </xacro:macro>

    <xacro:add_support_wheel name="front" flag="1" />
    <xacro:add_support_wheel name="back" flag="-1" />

</robot>

<!-- my_camrea.urdf.xacro  -->
<robot name="my_camera" xmlns:xacro="http://wiki.ros.org/xacro">
    <!--  -->
    <xacro:property name="camera_length" value="0.01" /> <!-- (x) -->
    <xacro:property name="camera_width" value="0.025" /> <!-- (y) -->
    <xacro:property name="camera_height" value="0.025" /> <!-- (z) -->
    <xacro:property name="camera_x" value="0.08" /> <!--  -->
    <xacro:property name="camera_y" value="0.0" /> <!--  -->
    <xacro:property name="camera_z" value="${base_link_length / 2 + camera_height / 2}" /> <!--   -->

    <!--  -->
    <link name="camera">
        <visual>
            <geometry>
                <box size="${camera_length} ${camera_width} ${camera_height}" />
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0" />
            <material name="black" />
        </visual>
    </link>

    <joint name="camera2base_link" type="fixed">
        <parent link="base_link" />
        <child link="camera" />
        <origin xyz="${camera_x} ${camera_y} ${camera_z}" />
    </joint>
</robot>

<!-- my_laser.urdf.xacro -->
<robot name="my_laser" xmlns:xacro="http://wiki.ros.org/xacro">

    <!--  -->
    <xacro:property name="support_length" value="0.15" /> <!--  -->
    <xacro:property name="support_radius" value="0.01" /> <!--  -->
    <xacro:property name="support_x" value="0.0" /> <!--  -->
    <xacro:property name="support_y" value="0.0" /> <!--  -->
    <xacro:property name="support_z" value="${base_link_length / 2 + support_length / 2}" /> <!--  -->

    <link name="support">
        <visual>
            <geometry>
                <cylinder radius="${support_radius}" length="${support_length}" />
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0" />
            <material name="red">
                <color rgba="0.8 0.2 0.0 0.8" />
            </material>
        </visual>
    </link>

    <joint name="support2base_link" type="fixed">
        <parent link="base_link" />
        <child link="support" />
        <origin xyz="${support_x} ${support_y} ${support_z}" />
    </joint>


    <!--  -->
    <xacro:property name="laser_length" value="0.05" /> <!--  -->
    <xacro:property name="laser_radius" value="0.03" /> <!--  -->
    <xacro:property name="laser_x" value="0.0" /> <!--  -->
    <xacro:property name="laser_y" value="0.0" /> <!--  -->
    <xacro:property name="laser_z" value="${support_length / 2 + laser_length / 2}" /> <!--  -->

    <!--  -->
    <link name="laser">
        <visual>
            <geometry>
                <cylinder radius="${laser_radius}" length="${laser_length}" />
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0" />
            <material name="black" />
        </visual>
    </link>

    <joint name="laser2support" type="fixed">
        <parent link="support" />
        <child link="laser" />
        <origin xyz="${laser_x} ${laser_y} ${laser_z}" />
    </joint>
</robot>

<!-- my_car_camera_laser.urdf.xacro -->
<robot name="my_car_camera_laser" xmlns:xacro="http://wiki.ros.org/xacro">
    <xacro:include filename="my_car.urdf.xacro" />
    <xacro:include filename="my_camera.urdf.xacro" />
    <xacro:include filename="my_laser.urdf.xacro" />

</robot>
cd launch
gedit my_car_camera_laser.launch
// 填入如下内容
<launch>
    <param name="robot_description" command="$(find xacro)/xacro $(find demo_pkg)/urdf/xacro/my_car_camera_laser.urdf.xacro" />

    <node pkg="rviz" type="rviz" name="rviz"  />
    <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" output="screen" />
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" output="screen" />
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" output="screen" />
</launch>
// 进入工作空间内进行编译
cd catkin_ws
catkin_make

// 执行权限
source devel/setup.bash

// 启动launch文件
roslaunch demo_pkg my_car_camera_laser.launch

// Rviz启动后,将对Rviz界面进行设置【同上面】,设置好后将其保存进config文件夹内,命名my_car_camera_laser.rviz
config/my_car_camera_laser.rviz

// 修改my_car.launch
// 修改如下:指定了Rviz的路径

<launch>
    <param name="robot_description" command="$(find xacro)/xacro $(find demo_pkg)/urdf/xacro/my_car_camera_laser.urdf.xacro"/>

    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find demo_pkg)/config/my_car_camera_laser.rviz"/>
    <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" output="screen" />
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" output="screen" />
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" output="screen" />
</launch>

// 再次启动launch文件
roslaunch demo_pkg my_car_camera_laser.launch

// 会看到模型就在打开的Rviz界面内。


 
 

7、URDF 集成Gazebo

URDF 与 Gazebo 集成流程与 Rviz 实现类似,主要步骤如下:

1. 创建功能包,导入依赖项
2. 编写 URDF 或 Xacro 文件
3. 启动 Gazebo 并显示机器人模型

 

7.1 创建功能包

创建新功能包,导入依赖包: urdf、xacro、gazebo_ros、gazebo_ros_control、gazebo_plugins


// 创建工作空间 并 初始化
mkdir -p catkin_ws/src
cd catkin_ws
catkin_make

// 创建Ros功能包 并 导入依赖
cd catkin_ws/src
catkin_create_pkg demo_pkg urdf xacro gazebo_ros gazebo_ros_control gazebo_plugins



 

7.2 编写URDF文件


// 新建功能包内的文件夹
mkdir urdf
mkdir launch
mkdir config

cd urdf
gedit urdf01_helloworld.urdf
// 填入如下内容
<!-- 
    创建一个机器人模型(盒状即可),显示在 Gazebo 中 
-->

<robot name="mycar">
    <link name="base_link">
        <visual>
            <geometry>
                <box size="0.5 0.2 0.1" />
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0" />
            <material name="yellow">
                <color rgba="0.5 0.3 0.0 1" />
            </material>
        </visual>
        <collision>
            <geometry>
                <box size="0.5 0.2 0.1" />
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0" />
        </collision>
        <inertial>
            <origin xyz="0 0 0" />
            <mass value="6" />
            <inertia ixx="1" ixy="0" ixz="0" iyy="1" iyz="0" izz="1" />
        </inertial>
    </link>
    <gazebo reference="base_link">
        <material>Gazebo/Blue</material>
    </gazebo>

</robot>

注意, 当 URDF 需要与 Gazebo 集成时,和 Rviz 有明显区别:
1.必须使用 collision 标签,因为既然是仿真环境,那么必然涉及到碰撞检测,collision 提供碰撞检测的依据。
2.必须使用 inertial 标签,此标签标注了当前机器人某个刚体部分的惯性矩阵,用于一些力学相关的仿真计算。
3.颜色设置,也需要重新使用 gazebo 标签标注,因为之前的颜色设置为了方便调试包含透明度,仿真环境下没有此选项。

 

7.3 启动Gazebo并显示模型


cd launch
gedit urdf01_helloworld.launch
// 填入如下内容
<launch>

    <!-- 将 Urdf 文件的内容加载到参数服务器 -->
    <param name="robot_description" textfile="$(find demo02_urdf_gazebo)/urdf/urdf01_helloworld.urdf" />

    <!-- 启动 gazebo -->
    <include file="$(find gazebo_ros)/launch/empty_world.launch" />

    <!-- 在 gazebo 中显示机器人模型 -->
    <node pkg="gazebo_ros" type="spawn_model" name="model" args="-urdf -model mycar -param robot_description"  />
</launch>

<!-- 代码解释:-->

<include file="$(find gazebo_ros)/launch/empty_world.launch" />
<!-- 启动 Gazebo 的仿真环境,当前环境为空环境 -->

<node pkg="gazebo_ros" type="spawn_model" name="model" args="-urdf -model mycar -param robot_description"  />

<!-- 
    在 Gazebo 中加载一个机器人模型,该功能由 gazebo_ros 下的 spawn_model 提供:
    -urdf 加载的是 urdf 文件
    -model mycar 模型名称是 mycar
    -param robot_description 从参数 robot_description 中载入模型
    -x 模型载入的 x 坐标
    -y 模型载入的 y 坐标
    -z 模型载入的 z 坐标
-->

 
 

8、xacro 集成Gazebo

在 ctrl+c 退出gazebo时,出现killed

在这里插入图片描述

再次启动roslaunch时,就会报如下错误:

翻译过来的意思就是说:
“执行XXX/gzserver 时进程挂掉,程序退出;
 执行XXX/gzclient 时进程挂掉,程序退出。”
 
根据报错解释可以确定,主要是gazebo在之前的操作中打开过,而没有完全的关闭,使用ctrl+c仅关闭了了gazebo的gui界面,并没有完全关闭gazebo。

解决方法:终端执行 killall gzserver && killall gzclient


// 解决方法---输入如下指令:
killall gzserver && killall gzclient 


[gazebo-1] process has died [pid 108415, exit code 255, cmd /opt/ros/melodic/lib/gazebo_ros/gzserver -e ode /home/hzx/hzx_ws/demo_gazebo_ws/src/demo_gazebo/world/box_house.world __name:=gazebo __log:=/home/hzx/.ros/log/fd9008b8-0d3a-11ef-9a38-000c29915674/gazebo-1.log].
log file: /home/hzx/.ros/log/fd9008b8-0d3a-11ef-9a38-000c29915674/gazebo-1*.log


[gazebo_gui-2] process has died [pid 108418, exit code 134, cmd /opt/ros/melodic/lib/gazebo_ros/gzclient __name:=gazebo_gui __log:=/home/hzx/.ros/log/fd9008b8-0d3a-11ef-9a38-000c29915674/gazebo_gui-2.log].
log file: /home/hzx/.ros/log/fd9008b8-0d3a-11ef-9a38-000c29915674/gazebo_gui-2*.log

在这里插入图片描述



8.1

报如下错误:Error [Converter.cc:151] Unable to convert from SDF version 1.7 to 1.6

翻译过来的意思就是说:
“无法将SDF的版本从1.7转成1.6”

根据报错解释可以确定在执行world.launch 文件时出现了错误,通过查看world.launch文件,发现启动该launch文件时调用了如下三个文件:。

在这里插入图片描述

具体三个文件如下:
 1、my_car_camera_laser.urdf.xacro
 2、empty_world.launch
 3、box_house.world

通过逐个文件排查,发现是 3、box_house.world 文件存在问题,

在这里插入图片描述

解决方法:将box_house.world中的 1.7 改写成 1.6 就可以正常启动了。

在这里插入图片描述


 
 

报如下错误:UnicodeEncodeError: ‘ascii’ codec can’t encode characters in position 7323-7324: ordinal not in range(128)

翻译过来的意思就是说:
“Unicode编码错误:“ascii”编解码器无法对位置7323-7324中的字符进行编码:序号不在范围内(128)”

根据报错解释可以确定,在启动 my_sensors_car_camera_laser.launch文件时需要调用一些xacro文件,这些文件中应该是存在中文,导致编码错误。 ubuntu18.04 melodic版本中一般使用python2.7环境,该环境下urdf文件中不能有中文注释出现,否则报错


解决方法一:将调用的xacro文件中的中文全部去掉即可。

在这里插入图片描述

解决方法二:进行一些设置,可以避免报 error,但会引入其他问题【引入的问题不影响启动xacro文件】参考链接在此。


  //  urdf文件不注释阅读起来很麻烦,可以通过如下解决:

//   cd到根目录下

cd /opt/ros/melodic/lib/python2.7/dist-packages 

sudo gedit sitecustomize.py

 // 在其中添加如下内容:

    #coding=utf8
    import sys
    reload(sys)
    sys.setdefaultencoding('utf8')
                        


// 引入的问题如下:
Error in sitecustomize; set PYTHONVERBOSE for traceback:
NameError: name 'reload' is not defined
Error in sitecustomize; set PYTHONVERBOSE for traceback:
NameError: name 'reload' is not defined

// 不影响启动 xacro 文件,介意者可以选择方法一。

在这里插入图片描述


 
 

在这里插入图片描述

9、载入

在这里插入图片描述
 
 

100、ROS过程中的错误

1. RLException: multiple files named XXX


hzx@vm:~/hzx_ws/demo_gazebo_ws$ roslaunch demo_gazebo my_sensors_car_camera_laser.urdf.xacro 
RLException: multiple files named [my_sensors_car_camera_laser.urdf.xacro] in package [demo_gazebo]:
- /home/hzx/hzx_ws/demo_gazebo_ws/src/demo_gazebo/urdf/xacro/my_sensors_car_camera_laser.urdf.xacro
- /home/hzx/hzx_ws/demo_gazebo_ws/src/demo_gazebo/launch/my_sensors_car_camera_laser.urdf.xacro
Please specify full path instead
The traceback for the exception was written to the log file

在这里插入图片描述

翻译过来的意思就是说:
“报了一个RLException错误,在【demo_gazebo】功能包内,有多个叫做【my_sensors_car_camera_laser.urdf.xacro】的文件,
并且之后也给你指出了这重名文件的各个路径。”

根据报错解释可以明显的发现问题所在,直接修改重名文件即可。

 

2、RLException: Invalid roslaunch XML syntax: no root < launch> tag

hzx@vm:~/hzx_ws/demo_gazebo_ws$ roslaunch demo_gazebo my_sensors_car_camera_laser.urdf.xacro
... logging to /home/hzx/.ros/log/fd9008b8-0d3a-11ef-9a38-000c29915674/roslaunch-vm-110873.log
Checking log directory for disk usage. This may take a while.
Press Ctrl-C to interrupt
Done checking log file disk usage. Usage is <1GB.

RLException: Invalid roslaunch XML syntax: no root <launch> tag
The traceback for the exception was written to the log file

在这里插入图片描述

翻译过来的意思就是说:
“ 报了一个RLException错误,无效的roslaunch XML语法:没有根< launch>标记 ”

根据报错解释可以明显的发现问题所在,执行roslaunch时,选定的launch文件有问题,一看确实有问题,修改launch文件就好了。


 

3、RLException: [my_sensors_car_camera_laser.launch] is neither a launch

报如下错误:RLException: [my_sensors_car_camera_laser.launch] is neither a launch file in package [demo_gazebo] nor is [demo_gazebo] a launch file name

翻译过来的意思就是说:
“XXX.launch 既不是demo_gazebo 功能包内的launch文件,也不是demo_gazebo 功能包内的launch文件名”

根据报错解释可以确定,此刻并未将devel/setup.bash添加到系统。

在这里插入图片描述


解决方法:进入工作空间,执行source,具体如下:


hzx@vm:~/hzx_ws/demo_gazebo_ws$ source devel/setup.bash 


第三


5号大小

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/614122.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

1.基于python的单细胞数据预处理-降维可视化

目录 降维的背景PCAt-sneUMAP检查质量控制中的指标 参考&#xff1a; [1] https://github.com/Starlitnightly/single_cell_tutorial [2] https://github.com/theislab/single-cell-best-practices 降维的背景 虽然特征选择已经减少了维数&#xff0c;但为了可视化&#xff0…

pikachu靶场-全套学习

文章目录 配置pikachu靶场浏览器访问过程burpsuite配置代理hackbar安装使用kali安装中国蚁剑暴力破解cookie简化场景解释各部分含义如何工作 基于表单的暴力破解验证码绕过(On server)验证码绕过(on client)token防爆破? XSS&#xff08;Cross-Site Scripting跨站脚本攻击 &am…

牛客NC142 最长重复子串【中等 字符串 Java/Go/C++】

题目 题目链接&#xff1a; https://www.nowcoder.com/practice/4fe306a84f084c249e4afad5edf889cc 思路 注意&#xff1a;题目给的时间复杂度是O(N^2)那么直接套用双重循环&#xff1a;外层循环i为假定起始重复子串的初始位置&#xff0c;内层循环的j为假定重复子串的结束位置…

【LeetCode算法】28. 找出字符串中第一个匹配项的下标

提示&#xff1a;此文章仅作为本人记录日常学习使用&#xff0c;若有存在错误或者不严谨得地方欢迎指正。 文章目录 一、题目二、思路三、解决方案四、JAVA截取字符串的常用方法4.1 通过subString()截取字符串* 一、题目 给你两个字符串 haystack 和 needle &#xff0c;请你在…

ubuntu安装oceanbase调通本地navicat链接

分为两部分 一安装oceanbase服务 准备工作 mkdir -p /data/1 /data/log1 chown -R admin.admin /data/1 /data/log1/偷偷说&#xff1a;其实这步我忘记执行&#xff0c;也没影响我安装 oceanbase程序是很占内存的在安装时我们要先下载好安装包&#xff1a; 然后放在能记住的…

react引入阿里矢量库图标

react引入阿里矢量库图标 登录阿里矢量库&#xff0c;将项目所需的图标放一起 react项目中新建文件夹MyIcon.js 3. 在页面中引入&#xff0c;其中type为图标名称

机器人系统ros2-开发实践08-了解如何使用 tf2 来访问坐标帧转换(Python)

tf2 库允许你在 ROS 节点中查询两个帧之间的转换。这个查询可以是阻塞的&#xff0c;也可以是非阻塞的&#xff0c;取决于你的需求。下面是一个基本的 Python 示例&#xff0c;展示如何在 ROS 节点中使用 tf2 查询帧转换。 本教程假设您已完成tf2 静态广播器教程 (Python)和tf…

探索循环购模式:消费返利与积分机制的创新融合

大家好&#xff0c;我是吴军&#xff0c;今天非常荣幸能与大家分享一种别具一格的商业模式——循环购模式。这种商业模式在近年来逐渐崭露头角&#xff0c;受到了广大消费者的热烈追捧。或许您之前听说过消费满额即送现金的活动&#xff0c;但循环购模式不仅仅局限于此&#xf…

单细胞分析:多模态 reference mapping (2)

引言 本文[1]介绍了如何在Seurat软件中将查询数据集与经过注释的参考数据集进行匹配。我们展示了如何将来自不同个体的人类骨髓细胞&#xff08;Human BMNC&#xff09;的人类细胞图谱&#xff08;Human Cell Atlas&#xff09;数据集&#xff0c;有序地映射到一个统一的参考框…

数据库数据恢复—Sql Server数据库文件丢失丢失怎么恢复数据?

数据库数据恢复环境&#xff1a; 5块硬盘组建一组RAID5阵列&#xff0c;划分LUN供windows系统服务器使用。windows系统服务器内运行了Sql Server数据库&#xff0c;存储空间在操作系统层面划分了三个逻辑分区。 数据库故障&#xff1a; 数据库文件丢失&#xff0c;主要涉及3个…

【微信开发】微信支付前期准备工作(申请及配置)

1、申请并配置公众号或微信小程序 1.1 账户申请 通过微信公众平台&#xff0c;根据指引申请微信小程序或公众号&#xff0c;申请时需要微信认证&#xff0c;申请流程不在赘述 1.2 信息配置 申请通过后&#xff0c;需进入小程序和公众号内进行信息配置 1.2.1 小程序信息配置…

如何批量将十六进制数据转成bin文件

最近在做新项目遇到一个问题&#xff0c;我们要通过上位机把一堆数据通过串口发送给下位机存储&#xff0c;而上位机需要Bin文件。 解决办法&#xff1a; 1)创建一个记事本文件&#xff0c;然后将其后缀修改成.bin 2)然后打开notepad,新建一个文件&#xff0c;随便写下数据 我…

怎么制作流程图?介绍制作方法

怎么制作流程图&#xff1f;在日常生活和工作中&#xff0c;流程图已经成为我们不可或缺的工具。无论是项目规划、流程优化&#xff0c;还是学习理解复杂系统&#xff0c;流程图都能帮助我们更直观地理解和表达信息。然而&#xff0c;很多人可能并不清楚&#xff0c;其实制作流…

【Linux】基础命令,文件处理,用户,vim编辑器,文件压缩

常用命令及参数&#xff1a;dir表示文件夹&#xff0c;file表示文件&#xff08;file可表示其他目录下的文件&#xff09; pwd命令&#xff1b;查看当前所属文件夹&#xff08;print working directory&#xff09; ls [选项] dir&#xff1b;查看当前、指定文件夹目录内容&am…

2.使用即时设计做页面原型

文章目录 1. 设计工具1.1. 上手1.2. 上手"即时设计"1.3. 产品原型偷师 2. 即时设计tips2.1. 完成后的效果图2.2. 画板 - iPhone容器2.3. 工具箱2.4. 画iPhone的状态栏和indicator2.4.1. 设计标准2.4.2. 小程序状态栏2.4.3. iPhone的indicator 2.5. 引入iconfont2.6. …

安全继电器的使用和作用

目录 一、什么是安全继电器 二、安全继电器的接线方式 三、注意事项 四、总结 一、什么是安全继电器 安全继电器是由多个继电器与硬件电路组合而成的一种模块&#xff0c;是一种电路组成单元&#xff0c;其目的是要提高安全因素。完整点说&#xff0c;应该叫成安全继电器模…

激光测径仪在胶管生产中扮演着什么角色?

关键词&#xff1a;激光测径仪,胶管,胶管测径仪,在线测径仪 胶管生产的基本工序为混炼胶加工、帘布及帆布加工、胶管成型、硫化等。不同结构及不同骨架的胶管&#xff0c;其骨架层的加工方法及胶管成型设备各异。 全胶胶管因不含骨架层&#xff0c;只需使用压出机压出胶管即可&…

APP广告转化流程对广告变现收益有影响吗?

对接广告平台做广告变现的APP开发者都清楚&#xff0c;广告变现的价格、收益不是一成不变的&#xff0c;经常会遇到eCPM波动对广告收益产生较大影响。 导致APP收益产生波动的因素包括&#xff1a;用户质量、广告类型、广告平台的资源波动、广告预算的季节性、广告展示量级等。…

【软考高项】四十一、十大管理记忆技巧

一、技巧1&#xff1a;绩效数据、信息、报告的流向 监控过程组除了 整合管理的2个过程&#xff0c;其余都有 绩效数据作为输入 监督风险 的输入同时有绩效数据和绩效报告 二、技巧2&#xff1a;可交付成果、核实的可交付成果、验收的可交付成果 三、技巧3&#xff1a;变更请求、…

Ansible之Playbook的Template模板和tags标签

文章目录 一、Template模块1、准备template模板文件2、修改主机清单文件3、编写playbook4、执行playbook5、准备测试网页6、访问测试 二、tags模块1、编写脚本2、执行tags"xx01"3、执行tags"xx02" 一、Template模块 Jinja是基于Python的模块引擎。Templat…