ROS Series: Chapter 6 Robot Modeling

Article directory

6. Robot system simulation

1 Overview

**Robot system simulation:** is a technology that simulates a physical robot system through a computer. In ROS, there are three main contents involved in the simulation implementation: modeling the robot (URDF), creating a simulation environment (Gazebo) and perceiving the environment ( Rviz) and other systemic implementations.

Simulation advantages:

Simulation plays a pivotal role in the development of robot systems. Compared with physical robots in R&D and testing, simulation has the following significant advantages:

1. **Low cost: **The current cost of robots remains high, often hundreds of thousands, and simulation can greatly reduce costs and reduce risks

2. **Efficient: **The environment built is more diverse and flexible, which can improve test efficiency and test coverage

3. ** High security: ** In the simulation environment, there is no need to consider the problem of wear and tear

Simulation flaws:

The performance of the robot in the simulation environment and the actual environment is quite different. In other words, the simulation cannot completely simulate the real physical world, and there are some "distortion" situations. The reasons are:

1. The physics engine used by the emulator is not yet able to fully and accurately simulate the physical conditions of the real world

2. The emulator builds the absolute ideal situation of the joint driver (motor & gearbox), sensor and signal communication. Currently, it does not support the simulation of actual hardware defects or some critical states.

2. The basic process of URDF integrated Rviz

Description of Requirement:

Show a box robot in Rviz

Implementation process:

  1. Preparation: Create a new function package and import dependencies
  2. Core: write urdf file
  3. Core: Integrate URDF and Rviz in the launch file
  4. Display robot model in Rviz

1. Create a function package and import dependencies

Create a new feature package with a custom name and import dependent packages: urdfwithxacro

Under the current feature package, create a few more directories:

urdf: directory where urdf files are stored

meshes: Robot model rendering file (not used yet)

config: configuration file

launch: Store launch startup files

2. Write URDF file

Create a new sub-folder: (optional), add a file urdfin the folder , copy the following content:.urdf

<robot name="mycar">
    <link name="base_link">
        <visual>
            <geometry>
                <box size="0.5 0.2 0.1" />
            </geometry>
        </visual>
    </link>
</robot>
Copy

3. Integrate URDF and Rviz in the launch file

In launchthe directory, create a new launch file. The launch file needs to start Rviz and import the urdf file. After Rviz starts, it can automatically load the analysis urdffile and display the robot model. The core question: how to import the urdf file? In ROS, you can use The path of the urdf file is set to the parameter server, the parameter name used is: robot_description, the sample code is as follows:

<launch>

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

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

</launch>
Copy

4. Display the robot model in Rviz

After starting rviz, you will find that there is no boxed robot model. This is because the robot display component is not added by default and needs to be added manually. The adding method is as follows:[External link picture transfer failed, the source site may have an anti-theft link mechanism, it is recommended to save the picture and upload it directly (img-2XO1iRYZ-1670239754316)(http://www.autolabor.com.cn/book/ROSTutorials/assets/01_URDF %E6%96%87%E4%BB%B6%E6%89%A7%E8%A1%8Crviz%E9%85%8D%E7%BD%AE01.png)][External link picture transfer failed, source site There may be an anti-leeching mechanism, it is recommended to save the picture and upload it directly (img-8XRxLmmk-1670239754320) (http://www.autolabor.com.cn/book/ROSTutorials/assets/02_URDF%E6%96%87%E4%BB %B6%E6%89%A7%E8%A1%8Crviz%E9%85%8D%E7%BD%AE02.png)]insert image description here

After setting, it can be displayed normally

5. Optimize rviz startup

When the file is started repeatedly launch, the component configuration information before Rviz will not be saved automatically, and the operation of step 4 needs to be repeated. For the convenience of use, the following methods can be used to optimize:

First, save the current configuration into configthe directory [External link picture transfer failed, the source site may have an anti-theft link mechanism, it is recommended to save the picture and upload it directly (img-hkr2wM0H-1670239754330) (http://www.autolabor.com.cn/book/ROSTutorials/assets/10_rviz %E9%85%8D%E7%BD%AE%E4%BF%9D%E5%AD%98.png)]
. Then, launchadd parameters to the startup configuration of Rviz in the file: args, the value is set to-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>
Copy

When restarting, the previous component configuration can be included, which is more convenient and quick to use.

3. Detailed explanation of URDF syntax

  • The robot root tag, similar to the launch tag in the launch file
  • link Linkage label
  • joint joint label
  • gazebo The tags needed to integrate gazebo

3.1 Detailed explanation of URDF syntax 01_robot


robot

In urdf, in order to ensure the integrity of the xml syntax, the tag is used robotas the root tag. All link, joint and other tags must be included in the robot tag. In this tag, the name of the robot model can be set through the name attribute

1. Attributes

name: specifies the name of the robot model

2. Sub-tabs

All other tags are child tags

3.2 Detailed explanation of URDF syntax 02_link


link

The link tag in urdf is used to describe the appearance and physical properties of a certain part of the robot (that is, the rigid part), such as: robot base, wheels, lidar, camera... Each part corresponds to a link. In the link tag, you can Design a series of attributes such as shape, size, color, inertia matrix, collision parameters, etc. of the part[External link picture transfer failed, the source site may have an anti-theft link mechanism, it is recommended to save the picture and upload it directly (img-sKElfjJs-1670239754331)(http://www.autolabor.com.cn/book/ROSTutorials/assets/% E5%AE%98%E6%96%B901_link.png)]

1. Attributes

  • name —> Name the connecting rod

2. Sub-tabs

  • visual —> describe the appearance (the corresponding data is visual)
    • geometry sets the shape of the link
      • Label 1: box (box shape)
        • Attribute: size=length (x) width (y) height (z)
      • Label 2: cylinder (cylinder)
        • Attribute: radius=radius length=height
      • Label 3: sphere (sphere)
        • Attribute: radius=radius
      • Label 4: mesh (add skin to the connecting rod)
        • Attribute: filename=resource path (format: package: file )
    • origin sets the offset and tilt radian
      • Attribute 1: xyz=x offset y cheap z offset
      • Attribute 2: rpy=x roll y pitch z yaw (unit is radian)
    • Metrial set material properties (color)
      • Attribute: name
      • Tags: color
        • Attribute: rgba=red, green, blue weight value and transparency (each weight value and transparency value [0,1])
  • collision —> The collision property of the connecting rod
  • Inertial —> Inertia matrix of the connecting rod

3.3 Detailed explanation of URDF syntax 03_joint


joint

The joint tag in urdf is used to describe the kinematics and dynamics properties of the robot joints, and can also specify the safety limit of the joint movement. The two parts of the robot (referred to as the parent link and the child link) are connected in the form of "joints". Connection, different joints have different motion forms: rotation, sliding, fixation, rotation speed, rotation angle limitation... For example: the wheels installed on the base can rotate 360 ​​degrees, while the camera may be completely fixed on the base.

The data corresponding to the joint tag is not visible in the model[External link picture transfer failed, the source site may have an anti-theft link mechanism, it is recommended to save the picture and upload it directly (img-44yTaDfi-1670239754332)(http://www.autolabor.com.cn/book/ROSTutorials/assets/% E5%AE%98%E6%96%B902_link.png)]

1. Attributes

  • name —> Name the joint
  • type —> joint motion form
    • continuous: revolving joint, which can rotate infinitely around a single axis
    • revolute: revolute joint, similar to continues, but with rotation angle limit
    • prismatic: sliding joints, joints that move along a certain axis, with position limits
    • planer: a planar joint that allows translation or rotation in a direction orthogonal to the plane
    • floating: floating joints, allowing translational and rotational movements
    • fixed: fixed joints, special joints that do not allow movement

2. Sub-tabs

  • parent (required)

    The name of the parent link is a mandatory attribute:

    • link: The name of the parent link, which is the name of this link in the robot structure tree.
  • child (required)

    The name of the child link is a mandatory attribute:

    • link: The name of the child link, which is the name of this link in the robot structure tree.
  • origin

    • Attributes: xyz=offset on each axis rpy=offset arc on each axis.
  • axis

    • Attribute: xyz is used to set which joint axis to move around.

3.4 URDF exercises


Description of Requirement:

Create a four-wheel cylindrical robot model, the robot parameters are as follows, the chassis is cylindrical, the radius is 10cm, and the height is 8cm. The four wheels are composed of two driving wheels and two universal support wheels. The radius of the two driving wheels is 3.25cm. The width is 1.5cm, the two universal wheels are spherical, the radius is 0.75cm, and the distance between the chassis and the ground is 1.5cm (consistent with the diameter of the universal wheels)

Demo of expected results:img

1. Create a new urdf and launch file

urdf file: basic implementation

<robot name="mycar">
    <!-- <优化项> -->
    <link name="base_footprint">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <sphere radius="0.001"/>
            </geometry>
        </visual>
    </link>
    <!-- <底盘> -->
    <link name="base_link">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <!-- <1.1立方体 长宽高>  -->
                <!-- <box size="0.5 0.2 0.1"/> -->
                <!-- <1.2圆柱 半径、高度> -->
                <cylinder radius="0.1" length="0.08"/>
                <!-- <1.3球体 半径> -->
                <!-- <sphere radius="2"/> -->
                <!-- <1.4皮肤> -->
                <!-- <mesh filename="package://urdf01_rviz/meshes/autolabor_mini.stl" /> -->
            </geometry>
            <!-- <2.偏移量与倾斜弧度> -->
            <!-- <xyz坐标 rpy旋转角度3.14=180度 1.57=90度翻滚、俯仰、偏航> -->
            <!-- <无特殊情况不要在此处对xyz进行操作,影响后期TF坐标变换,可在下方joint操作 rpy可以操作> -->
            <origin xyz="0.0 0.0 0.0" rpy="0.0  0.0 0.0"/>
            <!-- <3.颜色>red green blue a透明度 取值范围[0,1]-->
            <material name="baselink_color">
                <color rgba="0.7 0.3 0.2 0.8"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节 关联footprint & baselink> -->
    <joint name="baselink2basefootprint" type="fixed">
        <!-- <设置偏移量> -->
        <origin xyz="0.0 0.0 0.055" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_footprint"/>
        <!-- <子级 link> -->
        <!-- <关节z偏移量 = 车体高度/2 + 离地间距 > -->
        <child link="base_link"/>
        <!-- <fixed不需要设置关节旋转参考的坐标轴> -->
        <!-- <axis xyz="0.0 0.0 0.0"/> -->
        <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
    </joint>

    <!-- <驱动轮01> -->
    <link name="left_Wheel">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <!-- <1.1立方体>  -->
                <!-- <box size="0.02 0.05 0.05"/> -->
                <!-- <1.2圆柱> -->
                <cylinder radius="0.0325" length="0.015"/>
                <!-- <1.3球体> -->
                <!-- <sphere radius="0.0075"/> -->
                <!-- <1.4皮肤> -->
                <!-- <mesh filename="package://urdf01_rviz/meshes/autolabor_mini.stl" /> -->
            </geometry>
            <!-- <2.偏移量与倾斜弧度> -->
            <!-- <xyz坐标 rpy旋转角度3.14=180度 1.57=90度翻滚、俯仰、偏航> -->
            <!-- <先使用默认后期要修改 为防止下沉应该上移动一半的高度> -->
            <!-- <无特殊情况不要在此处对xyz进行操作,影响后期TF坐标变换,可在下方joint操作 rpy可以操作> -->
            <origin xyz="0.0 0.0 0.0" rpy="1.5708 0.0 0.0"/>
            <!-- <3.颜色>red green blue a透明度 取值范围[0,1]-->
            <material name="Whell03_color">
                <color rgba="0.0 0.0 0.0 0.8"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节  关联baselink& Wheel_01> -->
    <joint name="LeftWheel2baselink" type="continuous">
        <!-- <设置偏移量> -->
        <!-- <
            x 无偏移
            y 车体半径
            z 车体高度/2 + 离地 - 车轮半径
    
        > -->
        <origin xyz="0.0 0.1 -0.0225" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_link"/>
        <!-- <子级 link> -->
        <child link="left_Wheel"/>
        <!-- <设置关节旋转参考的坐标轴> -->
        <axis xyz="0.0 1.0 0.0"/>
        <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
    </joint>

    <!-- <驱动轮02> -->
    <link name="right_Wheel">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <!-- <1.1立方体>  -->
                <!-- <box size="0.02 0.05 0.05"/> -->
                <!-- <1.2圆柱> -->
                <cylinder radius="0.0325" length="0.015"/>
                <!-- <1.3球体> -->
                <!-- <sphere radius="0.0075"/> -->
                <!-- <1.4皮肤> -->
                <!-- <mesh filename="package://urdf01_rviz/meshes/autolabor_mini.stl" /> -->
            </geometry>
            <!-- <2.偏移量与倾斜弧度> -->
            <!-- <xyz坐标 rpy旋转角度3.14=180度 1.57=90度翻滚、俯仰、偏航> -->
            <!-- <先使用默认后期要修改 为防止下沉应该上移动一半的高度> -->
            <!-- <无特殊情况不要在此处对xyz进行操作,影响后期TF坐标变换,可在下方joint操作 rpy可以操作> -->
            <origin xyz="0.0 0.0 0.0" rpy="1.5708 0.0 0.0"/>
            <!-- <3.颜色>red green blue a透明度 取值范围[0,1]-->
            <material name="Whell03_color">
                <color rgba="0.0 0.0 0.0 0.8"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节  关联baselink& Wheel_02> -->
    <joint name="RightWheel2baselink" type="continuous">
        <!-- <设置偏移量> -->
        <!-- <
            x 无偏移
            y 车体半径
            z 车体高度/2 + 离地 - 车轮半径
    
        > -->
        <origin xyz="0.0 -0.1 -0.0225" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_link"/>
        <!-- <子级 link> -->
        <child link="right_Wheel"/>
        <!-- <设置关节旋转参考的坐标轴> -->
        <axis xyz="0.0 1.0 0.0"/>
        <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
    </joint>

    <!-- <万向轮01> -->
    <link name="front_Wheel">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <!-- <1.1立方体>  -->
                <!-- <box size="0.02 0.05 0.05"/> -->
                <!-- <1.2圆柱> -->
                <!-- <cylinder radius="0.0325" length="0.015"/> -->
                <!-- <1.3球体> -->
                <sphere radius="0.0075"/>
                <!-- <1.4皮肤> -->
                <!-- <mesh filename="package://urdf01_rviz/meshes/autolabor_mini.stl" /> -->
            </geometry>
            <!-- <2.偏移量与倾斜弧度> -->
            <!-- <xyz坐标 rpy旋转角度3.14=180度 1.57=90度翻滚、俯仰、偏航> -->
            <!-- <先使用默认后期要修改 为防止下沉应该上移动一半的高度> -->
            <!-- <无特殊情况不要在此处对xyz进行操作,影响后期TF坐标变换,可在下方joint操作 rpy可以操作> -->
            <origin xyz="0.0 0.0 0.0" rpy="0.0  0.0 0.0"/>
            <!-- <3.颜色>red green blue a透明度 取值范围[0,1]-->
            <material name="Whell01_color">
                <color rgba="0.0 0.0 0.0 0.8"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节  关联baselink& Wheel_Universal_01> -->
    <joint name="FrontWheel2baselink" type="continuous">
        <!-- <设置偏移量> -->
        <!-- <
            x 小于车体半径
            y 无偏移
            z 车体高度/2 + 离地 - 车轮半径
    
        > -->
        <origin xyz="0.08 0.0 -0.0475" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_link"/>
        <!-- <子级 link> -->
        <child link="front_Wheel"/>
        <!-- <设置关节旋转参考的坐标轴> -->
        <axis xyz="1.0 1.0 0.0"/>
        <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
    </joint>



    <!-- <万向轮02> -->
    <link name="back_Wheel">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <!-- <1.1立方体>  -->
                <!-- <box size="0.02 0.05 0.05"/> -->
                <!-- <1.2圆柱> -->
                <!-- <cylinder radius="0.0325" length="0.015"/> -->
                <!-- <1.3球体> -->
                <sphere radius="0.0075"/>
                <!-- <1.4皮肤> -->
                <!-- <mesh filename="package://urdf01_rviz/meshes/autolabor_mini.stl" /> -->
            </geometry>
            <!-- <2.偏移量与倾斜弧度> -->
            <!-- <xyz坐标 rpy旋转角度3.14=180度 1.57=90度翻滚、俯仰、偏航> -->
            <!-- <先使用默认后期要修改 为防止下沉应该上移动一半的高度> -->
            <!-- <无特殊情况不要在此处对xyz进行操作,影响后期TF坐标变换,可在下方joint操作 rpy可以操作> -->
            <origin xyz="0.0 0.0 0.0" rpy="0.0  0.0 0.0"/>
            <!-- <3.颜色>red green blue a透明度 取值范围[0,1]-->
            <material name="Whell02_color">
                <color rgba="0.0 0.0 0.0 0.8"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节  关联baselink& Wheel_Universal_02> -->
    <joint name="BackWheel2baselink" type="continuous">
        <!-- <设置偏移量> -->
        <!-- <设置偏移量> -->
        <!-- <
            x 小于车体半径
            y 无偏移
            z 车体高度/2 + 离地 - 车轮半径
    
        > -->
        <origin xyz="-0.08 0.0 -0.0475" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_link"/>
        <!-- <子级 link> -->
        <child link="back_Wheel"/>
        <!-- <设置关节旋转参考的坐标轴> -->
        <axis xyz="1.0 1.0 0.0"/>
        <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
    </joint>


</robot>

launch file:

<launch>

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

    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf01_rviz)/config/show_mycar.rviz" />

    <!-- 添加关节状态节点 -->
    <!-- <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" /> -->
    <!-- 添加关节运动控制节点(应该在机器人状态发布节点之上防止抖动) -->
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" />
    <!-- 添加机器人状态发布节点 -->
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" />

</launch>

[External link image transfer failed, the source site may have an anti-leeching mechanism, it is recommended to save the image and upload it directly (img-PmcZuDCE-1670239754335) (C:\Users\Haotian\AppData\Roaming\Typora\typora-user-images \1669983533650.png)]

3.5 URDF Tools


In ROS, some tools are provided to facilitate the writing of URDF files, such as:

  • check_urdfcommand to check complex urdf files for syntax problems
  • urdf_to_graphizThe command can view the urdf model structure and display the hierarchical relationship of different links

Of course, before using the tool, you need to install it first. The installation command:sudo apt install liburdfdom-tools

1. check_urdf syntax check

Enter the directory to which the urdf file belongs, call: check_urdf urdf文件, if no exception is thrown, the file is legal, otherwise it is illegal

insert image description here

experiment:

insert image description here

Note that right-clicking into the first urdf folder will allow tab completion

2. urdf_to_graphiz structure view

Enter the directory to which the urdf file belongs, call: urdf_to_graphiz urdf文件, a pdf file will be generated in the current directory

insert image description here

4. URDF optimization_xacro


concept

Xacro is the abbreviation of XML Macros, Xacro is an XML macro language, which is programmable XML.

principle

Xacro can declare variables, solve them through mathematical operations, use process control to control the execution sequence, and encapsulate fixed logic through the implementation of similar functions, exposing the variable data required in the logic as parameters, thereby improving the code. Reusability and program security.

effect

Compared with pure URDF implementation, robot model files that are safer, more compact, and more readable can be written, and writing efficiency can be improved.

4.1 Xacro_Quick experience


Description of Requirement:

Using xacro to optimize the implementation of the driving wheel in the case in the previous section requires the use of variables to encapsulate the radius and height of the chassis, use mathematical formulas to dynamically calculate the joint point coordinates of the chassis, use Xacro macros to encapsulate the repeated code of the wheels and call the macro to create two wheels (note : Here, the basic use of Xacro is demonstrated, it is not necessary to generate legal URDF).

Prepare:

Create a function package and import urdf and xacro.

1. Xacro file writing

Write an Xacro file that encapsulates properties (constant radius, height, wheel radius...) as variables, and encapsulates repeated implementations (addition of wheels) as functions.

<robot name="mycar" xmlns:xacro="http://wiki.ros.org/xacro">
<!-- <
    1.代码复用     Xacro 宏定义 (函数调用)
    2.参数设计     Xacro 变量
> -->
    <!-- 属性封装 -->
    <xacro:property name="wheel_radius" value="0.0325" />
    <xacro:property name="wheel_length" value="0.0015" />
    <xacro:property name="PI" value="3.1415927" />
    <xacro:property name="base_link_length" value="0.08" />
    <xacro:property name="lidi_space" value="0.015" />

    <!-- 宏 -->
    <xacro:macro name="wheel_func" params="wheel_name flag" >
        <link name="${wheel_name}_wheel">
            <visual>
                <geometry>
                    <cylinder radius="${wheel_radius}" length="${wheel_length}" />
                </geometry>

                <origin xyz="0 0 0" rpy="${PI / 2} 0 0" />

                <material name="wheel_color">
                    <color rgba="0 0 0 0.3" />
                </material>
            </visual>
        </link>

        <!-- 3-2.joint -->
        <joint name="${wheel_name}2link" type="continuous">
            <parent link="base_link"  />
            <child link="${wheel_name}_wheel" />
            <!-- 
                x 无偏移
                y 车体半径
                z z= 车体高度 / 2 + 离地间距 - 车轮半径

            -->
            <origin xyz="0 ${0.1 * flag} ${(base_link_length / 2 + lidi_space - wheel_radius) * -1}" rpy="0 0 0" />
            <axis xyz="0 1 0" />
        </joint>

    </xacro:macro>
    <!-- <调用> -->
    <xacro:wheel_func wheel_name="left" flag="1" />
    <xacro:wheel_func wheel_name="right" flag="-1" />
</robot>

2. Convert Xacro file to urdf file

Use the command line to enter the directory where the xacro file belongs, and execute: rosrun xacro xacro xxx.xacro > xxx.urdf, the xacro file will be parsed into an urdf file.

Note: This case is written to generate an illegal URDF file, the purpose is to demonstrate the minimal use and advantages of Xacro.

4.2 Xacro_ grammar detailed explanation


xacro provides a programmable interface, similar to a computer language, including syntax implementations such as variable declaration and call, function declaration and call. When using xacro to generate urdf, robotthe namespace declaration must be included in the root tag:xmlns:xacro="http://wiki.ros.org/xacro"

1. Attributes and arithmetic operations

Used to encapsulate some fields in URDF, such as: PAI value, car size, wheel radius...

attribute definition

<xacro:property name="xxxx" value="yyyy" />

attribute call

${属性名称}

Arithmetic

${数学表达式}

2. Macro

Similar to function implementation, improve code reuse rate, optimize code structure, and improve security

macro definition

<xacro:macro name="宏名称" params="参数列表(多参数之间使用空格分隔)">

    .....

    参数调用格式: ${参数名}

</xacro:macro>

macro call

<xacro:宏名称 参数1=xxx 参数2=xxx/>

3. The file contains

The robot is composed of multiple parts, and different parts may be packaged into separate xacro files. Finally, different files are integrated and combined into a complete robot, which can be implemented using file inclusion

file contains

<robot name="xxx" xmlns:xacro="http://wiki.ros.org/xacro">
      <xacro:include filename="my_base.xacro" />
      <xacro:include filename="my_camera.xacro" />
      <xacro:include filename="my_laser.xacro" />
      ....
</robot>

4.3 Xacro_ complete usage process example


Description of Requirement:

Using Xacro to optimize the URDF version of the chassis model of the car

Demo of expected results:

img

1. Write Xacro file

<?xml version="1.0"?>
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
   
    <xacro:property name="footprint_radius" value="0.001"/>
    
     <link name="base_footprint">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
            <sphere radius="${footprint_radius}"/>
            </geometry>
        </visual>
    </link>
    <xacro:property name="base_radius" value="0.1"/>
    <xacro:property name="base_length" value="0.08"/>
    <xacro:property name="lidi" value="0.015"/>
    <xacro:property name="base_joint_z" value="${base_length / 2 + lidi}"/>
    <!-- <底盘> -->
    <link name="base_link">
        <!-- <可视化标签> -->
        <visual>
            <!-- <1.形状> -->
            <geometry>
                <cylinder radius="${base_radius}" length="${base_length}"/>
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0  0.0 0.0"/>
            <material name="baselink_color">
                <color rgba="0.7 0.3 0.2 0.5"/>
            </material>
        </visual>
    </link>
    <!-- <joint关节 关联footprint & baselink> -->
    <joint name="baselink2basefootprint" type="fixed">
        <!-- <设置偏移量> -->
        <origin xyz="0.0 0.0 ${base_joint_z}" rpy="0.0 0.0 0.0"/>
        <!-- <父级 link> -->
        <parent link="base_footprint"/>
        <!-- <子级 link> -->
        <!-- <关节z偏移量 = 车体高度/2 + 离地间距 > -->
        <child link="base_link"/>
    </joint>

    <xacro:property name="wheel_radius" value="0.0325"/>
    <xacro:property name="wheel_length" value="0.015"/>
    <xacro:property name="PI" value="3.1415927"/>
    <!-- <结果是负数> -->
    <xacro:property name="wheel_joint_z" value="${(base_length / 2 + lidi - wheel_radius) * -1}"/>
   
    <xacro:macro name="wheel_func" params="wheel_name flag">
    <!-- <
        wheel_name : left or right
        flag : 1 or -1 right/left wheel
    > -->
    <!-- <驱动轮01> -->
        <link name="${wheel_name}">
            <!-- <可视化标签> -->
            <visual>
                <!-- <1.形状> -->
                <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="whell03_color">
                    <color rgba="0.0 0.0 0.0 0.8"/>
                </material>
            </visual>
        </link>
        <!-- <joint关节  关联baselink& Wheel_01> -->
        <joint name="${wheel_name}2baselink" type="continuous">
            <!-- <设置偏移量> -->
            <!-- <
                x 无偏移
                y 车体半径
                z 车体高度/2 + 离地 - 车轮半径
            > -->
            <origin xyz="0.0 ${flag * 0.1} ${wheel_joint_z}" rpy="0.0 0.0 0.0"/>
            <!-- <父级 link> -->
            <parent link="base_link"/>
            <!-- <子级 link> -->
            <child link="${wheel_name}"/>
            <!-- <设置关节旋转参考的坐标轴> -->
            <axis xyz="0.0 1.0 0.0"/>
            <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
        </joint>
    </xacro:macro>
    <xacro:wheel_func wheel_name="base_l_wheel_joint" flag="1"/>
    <xacro:wheel_func wheel_name="base_r_wheel_joint" flag="-1"/>


    <xacro:property name="sup_wheel_radius" value="0.0075"/>
     <xacro:property name="sup_wheel_joint_x" value="${base_radius - sup_wheel_radius }"/>
     <!-- <结果是负数> -->
    <xacro:property name="sup_wheel_joint_z" value="${(base_length / 2 + lidi - sup_wheel_radius ) * -1}"/>


    <xacro:macro name="sup_wheel_func" params="name flag">
        <!-- <万向轮01> -->
        <link name="${name}_wheel">
            <!-- <可视化标签> -->
            <visual>
                <!-- <1.形状> -->
                <geometry>
                    <sphere radius="${sup_wheel_radius}"/>
                </geometry>
                <origin xyz="0.0 0.0 0.0" rpy="0.0  0.0 0.0"/>
                <material name="whell01_color">
                    <color rgba="0.0 0.0 0.0 0.8"/>
                </material>
            </visual>
        </link>
        <!-- <joint关节  关联baselink& Wheel_Universal_01> -->
        <joint name="${name}2baselink" type="continuous">
            <!-- <设置偏移量> -->
                    <!-- <
                x 小于车体半径 自定义  底盘半径-万象轮半径=0.1-0.0075=0.0925
                y 无偏移
                z 车体高度/2 + 离地 - 车轮直径
            > -->
            <origin xyz="${sup_wheel_joint_x * flag } 0.0 ${sup_wheel_joint_z}" rpy="0.0 0.0 0.0"/>
            <!-- <父级 link> -->
            <parent link="base_link"/>
            <!-- <子级 link> -->
            <child link="${name}_wheel"/>
            <!-- <设置关节旋转参考的坐标轴> -->
            <axis xyz="1.0 1.0 1.0"/>
            <!-- <limit lower="0.0" upper="0.0" effort="0.0" velocity="0.0"/> -->
        </joint>
    </xacro:macro>
    <xacro:sup_wheel_func name="front" flag="1"/>
    <xacro:sup_wheel_func name="back" flag="-1"/>

</robot>

2. Integrate the launch file

**Method 1:** first convert the xacro file to urdf file, and then integrate

First parse the xacro file into an urdf file: rosrun xacro xacro xxx.xacro > xxx.urdfthen directly integrate the launch file according to the previous integration method;

**Method 2:** Load xacro directly in the launch file ( recommended )

Launch content example:

<launch>

    <!-- 设置参数 -->
    <!-- <param name="robot_description" textfile="$(find urdf01_rviz)/urdf/xacro/demo05_car_base.urdf" /> -->
     <param name="robot_description" command="$(find xacro)/xacro $(find urdf01_rviz)/urdf/xacro/demo05_car_base.xacro" />
    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf01_rviz)/config/show_mycar.rviz" />
    <!-- 添加关节状态节点 -->
    <!-- <node pkg="joint_state_publisher" type="joint_state_publisher" name="joint_state_publisher" /> -->
    <!-- 添加关节运动控制节点(应该在机器人状态发布节点之上防止抖动) -->
    <node pkg="joint_state_publisher_gui" type="joint_state_publisher_gui" name="joint_state_publisher_gui" />
    <!-- 添加机器人状态发布节点 -->
    <node pkg="robot_state_publisher" type="robot_state_publisher" name="robot_state_publisher" />

</launch>

Core code:

 <param name="robot_description" command="$(find xacro)/xacro $(find urdf01_rviz)/urdf/xacro/demo05_car_base.xacro" />

robot_descriptionThe attribute is used when loading command, and the attribute value is to call the xacro program of the xacro function package to directly parse the xacro file.

4.4 Detailed explanation of URDF syntax 01_robot


Description of Requirement:

On the basis of the front car chassis, add cameras and radar sensors.

Result demo:

insert image description here

Realize analysis:

The robot model is composed of multiple parts, and different components can be set into separate files, and finally the assembly of components can be realized through file inclusion.

Implementation process:

  1. First write the xacro file of camera and radar
  2. Then write a combined file to combine the chassis, camera and radar
  3. Finally, start Rviz through the launch file and display the model

1. Camera and radar Xacro file implementation

Camera xacro file:

<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <!-- <摄像头> -->
    <!-- <
        1.连杆属性:厚度(x)宽度(y) 高度(z)
        2.关节属性: x y z
    > -->

    <xacro:property name="camera_length" value="0.02"/>
    <xacro:property name="camera_width" value="0.05"/>
    <xacro:property name="camera_hight" value="0.05"/>

    <xacro:property name="joint_camera_x" value="0.08"/>
    <xacro:property name="joint_camera_y" value="0.0"/>
    <xacro:property name="joint_camera_z" value="${base_length / 2 +  camera_length / 2 + lidi }"/>
    
    <link name="camera">
      
        <visual>
        <geometry>
            <box size="${camera_length} ${camera_width} ${camera_hight}"/>
        </geometry>
        <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
        <material name="camera_black">
            <color rgba="0.0 0.0 0.0 1.0"/>
        </material>
        </visual>

    </link>
    <joint name="camera2base" type="fixed">
        <parent link="base_link"/>
        <child link="camera"/>
        <origin xyz="${joint_camera_x} ${joint_camera_y} ${joint_camera_z}" rpy="0.0 0.0 0.0"/>
    </joint>
    

</robot>

Radar xacro file:

<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <!-- <雷达> -->
    <!-- <
        1.支撑尺寸:高度 半径
        2.关节属性: x y z

        1.雷达尺寸:高度 半径
        2.关节属性: x y z
    > -->
    <xacro:property name="support_radius" value="0.01"/>
    <xacro:property name="support_length" value="0.15"/>

    <xacro:property name="joint_support_x" value="0"/>
    <xacro:property name="joint_support_y" value="0"/>
    <!-- z=车体高度/2+支撑高度/2  -->
    <xacro:property name="joint_support_z" value="${support_length / 2+ base_length / 2 }"/>

    <xacro:property name="laser_radius" value="0.03"/>
    <xacro:property name="laser_length" value="0.05"/>

    <xacro:property name="joint_laser_x" value="0"/>
    <xacro:property name="joint_laser_y" value="0"/>
    <xacro:property name="joint_laser_z" value="${support_length / 2+ laser_length / 2}"/>
    <!-- 支架 -->
    <link name="support">
        <visual>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
            <geometry>
                <cylinder radius="${support_radius}" length="${support_length}"/>
            </geometry>
            <material name="yellow">
                <color rgba="0.8 0.5 0.0 0.5"/>
            </material>
        </visual>
    </link>

    <joint name="support2baselink" type="fixed">
        <parent link="base_link"/>
        <child link="support"/>
        <origin xyz="${joint_support_x} ${joint_support_y} ${joint_support_z}" rpy="0.0 0.0 0.0"/>
    </joint>
    <!-- 雷达 -->
    <link name="laser">
        <visual>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
            <geometry>
                <cylinder radius="${laser_radius}" length="${laser_length}"/>
            </geometry>
            <material name="laser">
                <color rgba="0.0 0.0 0.0 0.5"/>
            </material>
        </visual>
    </link>
    <joint name="laser2supportlink" type="fixed">
        <parent link="support"/>
        <child link="laser"/>
        <origin xyz="${joint_laser_x} ${joint_laser_y} ${joint_laser_z}" rpy="0 0 0"/>
    </joint>

</robot>


2. Combine the xacro file of chassis camera and radar

<?xml version="1.0"?>
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <!-- <文件包含> -->

    <xacro:include filename="demo05_car_base.urdf.xacro"/>
    <xacro:include filename="demo06_car_camera.urdf.xacro"/>
    <xacro:include filename="demo07_car_laser.urdf.xacro"/>

</robot>

3. launch file

<launch>

    <!-- 设置参数 -->
    <!-- <param name="robot_description" textfile="$(find urdf01_rviz)/urdf/xacro/demo05_car_base.urdf" /> -->
    <param name="robot_description" command="$(find xacro)/xacro $(find urdf01_rviz)/urdf/xacro/car.urdf.xacro" />
    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf01_rviz)/config/show_mycar.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" />

</launch>

insert image description here

5. Control the movement of the robot model in Rviz

**Arbotix:**Arbotix is ​​a control board for controlling motors and servos, and provides a corresponding ros function package . The functions of this function package can not only drive the real Arbotix control board, but also provide a differential speed controller, Update the joint state of the robot by accepting the speed control command, which helps us realize the movement of the robot in rviz.

The differential controller is in the arbotix_python package, and the complete arbotix package also includes a variety of controllers, corresponding to dynamixel motors, multi-joint robotic arms, and grippers of different shapes.

Next, demonstrate the use of arbotix through a case.

Description of Requirement:

Control the robot model to do circular motion in rviz

Result demo:

insert image description here

Implementation process:

  1. Install Arbotix
  2. Create a new feature package, prepare robot urdf, xacro files
  3. Add Arbotix configuration file
  4. Write a launch file to configure Arbotix
  5. Start the launch file and control the movement of the robot model

1. Install Arbotix

**Method 1:**Command line call

sudo apt-get install ros-<<VersionName()>>-arbotix

Replace <<VsersionName()>> with the name of the current ROS version. If it prompts that the function package cannot be located, please use method 2.

**Method 2:**Source code installation

First download the source code from github, then call catkin_make to compile

git clone https://github.com/vanadiumlabs/arbotix_ros.git

2. Create a new function package and prepare the robot urdf and xacro

urdf and xacro can be implemented by calling the previous lecture

3. Add the configuration files required by arbotix

Add arbotix required configuration files

# 该文件是控制器配置,一个机器人模型可能有多个控制器,比如: 底盘、机械臂、夹持器(机械手)....
# 因此,根 name 是 controller
controllers: {
    
    
   # 单控制器设置
   base_controller: {
    
    
          #类型: 差速控制器
       type: diff_controller,
       #参考坐标
       base_frame_id: base_footprint, 
       #两个轮子之间的间距
       base_width: 0.2,
       #控制频率
       ticks_meter: 2000, 
       #PID控制参数,使机器人车轮快速达到预期速度
       Kp: 12, 
       Kd: 12, 
       Ki: 0, 
       Ko: 50, 
       #加速限制
       accel_limit: 1.0 
    }
}

See also: http://wiki.ros.org/arbotix_python/diff_controller

4. Configure the arbotix node in the launch file

launch sample code

<launch>

    <!-- 设置参数 -->
    <!-- <param name="robot_description" textfile="$(find urdf01_rviz)/urdf/xacro/demo05_car_base.urdf" /> -->
    <param name="robot_description" command="$(find xacro)/xacro $(find urdf01_rviz)/urdf/xacro/car.urdf.xacro" />
    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf01_rviz)/config/show_mycar.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" />
    <!-- 添加集成 arbotix 运动控制节点,并加载参数 -->
    <node pkg="arbotix_python" type="arbotix_driver" name="driver" output="screen">
        <rosparam command="load" file="$(find urdf01_rviz)/config/control.yaml" />
        <param name="sim" value="true"/>
        <!-- 可以控制现实和仿真环境,因此需要设置为仿真 -->


    </node>

</launch>

Code explanation:

Called the arbotix_driver node under the arbotix_python function package

When arbotix drives the robot to run, it needs to obtain robot information, and you can load the configuration file through file

In the simulation environment, you need to configure sim as true

5. Start the launch file and control the movement of the robot model

**Start launch:** roslaunch xxxx...launch

Start error:

Joint state with name: "base_l_wheel_joint" was received but not found in URDF

Reason: different name from arbotix configuration

demo05_car_base.urdf changes the names of the joint nodes of the left and right wheels to "base_l_wheel_joint" and "base_r_wheel_joint"

Convert xacro to urdf: rosrun xacro xacro demo05_car_base.urdf.xacro > demo05.urdf

Convert to pdf for viewing: urdf_to_graphiz urdf/demo05.urdf

insert image description here

Configure rviz:

insert image description here

Control the movement of the car:

Calling rostopic list at this time will find a familiar topic: /cmd_vel

insert image description here

rostopic pub -r 10 /cmd_vel geometry_msgs/Twist '{
    
    linear: {
    
    x: 0.2, y: 0, z: 0}, angular: {
    
    x: 0, y: 0, z: 0.5}}'

Please also refer to:

  • http://wiki.ros.org/arbotix

6. URDF integrates Gazebo

URDF needs to be integrated into Rviz or Gazebo to display the visualized robot model

6.1Basic integration process of URDF and Gazebo

The integration process of URDF and Gazebo is similar to that of Rviz, the main steps are as follows:

  1. Create a feature package and import dependencies
  2. Write URDF or Xacro files
  3. Start Gazebo and display the robot model

1. Create a feature package

Create a new feature package and import dependent packages: urdf, xacro, gazebo_ros, gazebo_ros_control, gazebo_plugins

2. Write URDF file

Note that when URDF needs to be integrated with Gazebo, it is significantly different from Rviz:

1. The collision tag must be used, because since it is a simulation environment, it must involve collision detection, and collision provides the basis for collision detection.

2. The inertia tag must be used. This tag marks the inertia matrix of a certain rigid body part of the current robot, which is used for some mechanical-related simulation calculations.

3. The color setting also needs to be re-labeled with the gazebo label, because the previous color setting includes transparency for the convenience of debugging, and there is no such option in the simulation environment

3. Start Gazebo and display the model

Code explanation:

<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 坐标
-->

6.2 URDF integrated Gazebo related settings

Compared with rviz, gazebo needs to make some modifications when integrating URDF. For example, parameters related to collision attributes must be added, and parameters related to inertia matrix must be added. In addition, if the color setting of the robot in Rviz is directly transplanted, it will not be displayed. The color settings must also be changed accordingly.

1.collision

If the robot link is a standard geometric shape, it can be set to be consistent with the visual attribute of the link.

2.inertial

The setting of the inertia matrix needs to be dynamically generated in combination with the quality and shape parameters of the link. In principle, except for the base_footprint, each rigid body part of the robot needs to set an inertia matrix, and the inertia matrix must be calculated. If you define the inertia of the rigid body part at will Matrix, it may cause the robot to shake and move in Gazebo.

3. Color settings

To display the color of the link in gazebo, the specified label must be used:

<gazebo reference="link节点名称">
     <material>Gazebo/Blue</material>
</gazebo>

**PS: **In the material tag, the value set is case-sensitive, and the color can be set to Red Blue Green Black ...

6.3 URDF integrated Gazebo practical operation requirements description:

Display the previous robot model (xacro version) in gazebo

Result demo:
insert image description here

Implementation process:

  1. Need to write the xacro file that encapsulates the inertia matrix algorithm
  2. Add collision and inertia tags to each link in the robot model, and reset the color attribute
  3. Start gazebo in the launch file and add the robot model

1. Write the xacro file that encapsulates the inertia matrix algorithm

<robot name="base" xmlns:xacro="http://wiki.ros.org/xacro">
    <!-- Macro for inertia matrix -->
    <xacro:macro name="sphere_inertial_matrix" params="m r">
        <inertial>
            <mass value="${m}" />
            <inertia ixx="${2*m*r*r/5}" ixy="0" ixz="0"
                iyy="${2*m*r*r/5}" iyz="0" 
                izz="${2*m*r*r/5}" />
        </inertial>
    </xacro:macro>

    <xacro:macro name="cylinder_inertial_matrix" params="m r h">
        <inertial>
            <mass value="${m}" />
            <inertia ixx="${m*(3*r*r+h*h)/12}" ixy = "0" ixz = "0"
                iyy="${m*(3*r*r+h*h)/12}" iyz = "0"
                izz="${m*r*r/2}" /> 
        </inertial>
    </xacro:macro>

    <xacro:macro name="Box_inertial_matrix" params="m l w h">
       <inertial>
               <mass value="${m}" />
               <inertia ixx="${m*(h*h + l*l)/12}" ixy = "0" ixz = "0"
                   iyy="${m*(w*w + l*l)/12}" iyz= "0"
                   izz="${m*(w*w + h*h)/12}" />
       </inertial>
   </xacro:macro>
</robot>

2. Copy the relevant xacro file, and set parameters such as collision inertia and color

A. Chassis Xacro file
<robot name="my_base"
    xmlns:xacro="http://www.ros.org/wiki/xacro">
    <!-- 封装变量、常量 -->
    <!-- PI 值设置精度需要高一些,否则后续车轮翻转量计算时,可能会出现肉眼不能察觉的车轮倾斜,从而导致模型抖动 -->

    <!-- 宏:黑色设置 -->
    <material name="black">
        <color rgba="0.0 0.0 0.0 1.0" />
    </material>

    <!-- 底盘属性 -->
    <xacro:property name="footprint_radius" value="0.001" />
    <xacro:property name="PI" value="3.1415926"/>
    <!-- base_footprint 半径  -->
    <xacro:property name="base_radius" value="0.1" />
    <!-- base_link 半径 -->
    <xacro:property name="base_length" value="0.08" />
    <!-- base_link 长 -->
    <xacro:property name="lidi" value="0.015" />
    <!-- 离地间距 -->
    <xacro:property name="base_mass" value="0.5" />
    <!-- 质量  -->
    <!-- 驱动轮属性 -->
    <xacro:property name="wheel_radius" value="0.0325" />
    <!-- 半径 -->
    <xacro:property name="wheel_length" value="0.015" />
    <!-- 宽度 -->
    <xacro:property name="wheel_mass" value="0.05" />
    <!-- 质量  -->
    <!-- 支撑轮属性 -->
    <xacro:property name="sup_wheel_radius" value="0.0075" />
    <!-- 支撑轮半径 -->
    <xacro:property name="sup_wheel_mass" value="0.03" />
    <!-- 质量  -->
    <!-- 底盘 -->
    <link name="base_footprint">
        <visual>
            <geometry>
                <sphere radius="${footprint_radius}" />
            </geometry>
        </visual>
    </link>
    <link name="base_link">
        <visual>
            <geometry>
                <cylinder radius="${base_radius}" length="${base_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>
        <collision>
            <geometry>
                <cylinder radius="${base_radius}" length="${base_length}" />
            </geometry>
            <origin xyz="0 0 0" rpy="0 0 0" />
        </collision>
        <xacro:cylinder_inertial_matrix m="${base_mass}" r="${base_radius}" h="${base_length}" />
    </link>
    <joint name="base_link2base_footprint" type="fixed">
        <parent link="base_footprint" />
        <child link="base_link" />
        <origin xyz="0 0 ${lidi + base_length / 2 }" />
    </joint>
    <gazebo reference="base_link">
        <material>Gazebo/Yellow</material>
    </gazebo>
    <!-- 驱动轮 -->
    <!-- 驱动轮宏实现 -->
    <xacro:macro name="wheel_func" 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>
            <collision>
                <geometry>
                    <cylinder radius="${wheel_radius}" length="${wheel_length}" />
                </geometry>
                <origin xyz="0.0 0.0 0.0" rpy="${PI / 2} 0.0 0.0" />
            </collision>
            <xacro:cylinder_inertial_matrix m="${wheel_mass}" r="${wheel_radius}" h="${wheel_length}" />

        </link>
        <joint name="${name}_wheel2base_link" type="continuous">
            <parent link="base_link" />
            <child link="${name}_wheel" />
            <origin xyz="0 ${flag * base_radius} ${-(lidi + base_length / 2 - wheel_radius) }" />
            <axis xyz="0 1 0" />
        </joint>

        <gazebo reference="${name}_wheel">
            <material>Gazebo/Red</material>
        </gazebo>
    </xacro:macro>
    <xacro:wheel_func name="left" flag="1" />
    <xacro:wheel_func name="right" flag="-1" />
    <!-- 支撑轮 -->
    <!-- 支撑轮宏 -->
    <xacro:macro name="sup_wheel_func" params="name flag">
        <link name="${name}_wheel">
            <visual>
                <geometry>
                    <sphere radius="${sup_wheel_radius}" />
                </geometry>
                <origin xyz="0 0 0" rpy="0 0 0" />
                <material name="black" />
            </visual>
            <collision>
                <geometry>
                    <sphere radius="${sup_wheel_radius}" />
                </geometry>
                <origin xyz="0 0 0" rpy="0 0 0" />
            </collision>
            <xacro:sphere_inertial_matrix m="${sup_wheel_mass}" r="${sup_wheel_radius}" />
        </link>

        <joint name="${name}_wheel2base_link" type="continuous">
            <parent link="base_link" />
            <child link="${name}_wheel" />
            <origin xyz="${flag * (base_radius - sup_wheel_radius)} 0 ${-(base_length / 2 + lidi / 2)}" />
            <axis xyz="1 1 1" />
        </joint>
        <gazebo reference="${name}_wheel">
            <material>Gazebo/Red</material>
        </gazebo>
    </xacro:macro>
    <xacro:sup_wheel_func name="front" flag="1" />
    <xacro:sup_wheel_func name="back" flag="-1" />
</robot>

Note: If the robot model shakes, slides, moves slowly, etc. in Gazebo, please check

  1. Whether the inertia matrix is ​​set, and whether the setting is correct and reasonable
  2. Wheel flipping needs to depend on PI value, if the accuracy of PI value is low, it may also lead to the above situation
B. Camera Xacro file
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <!-- <摄像头> -->
    <!-- <
        1.连杆属性:厚度(x)宽度(y) 高度(z)
        2.关节属性: x y z
    > -->

    <xacro:property name="camera_length" value="0.02"/>
    <xacro:property name="camera_width" value="0.05"/>
    <xacro:property name="camera_hight" value="0.05"/>
    <xacro:property name="camera_mass" value="0.01"/>

    <xacro:property name="joint_camera_x" value="0.08"/>
    <xacro:property name="joint_camera_y" value="0.0"/>
    <xacro:property name="joint_camera_z" value="${base_length / 2 +  camera_length / 2 + lidi }"/>

    <link name="camera">
        <visual>
            <geometry>
                <box size="${camera_length} ${camera_width} ${camera_hight}"/>
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
            <material name="camera_black">
                <color rgba="0.0 0.0 0.0 1.0"/>
            </material>
        </visual>
        <collision>
            <geometry>
                <box size="${camera_length} ${camera_width} ${camera_hight}"/>
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
        </collision>
        <xacro:Box_inertial_matrix m="${camera_mass}" l="${camera_length}" w="${camera_width}" h="${camera_hight}" />
    </link>

    <joint name="camera2base" type="fixed">
        <parent link="base_link"/>
        <child link="camera"/>
        <origin xyz="${joint_camera_x} ${joint_camera_y} ${joint_camera_z}" rpy="0.0 0.0 0.0"/>
    </joint>
    <gazebo reference="camera">
        <material>
            Gazebo/Blue 
        </material>
    </gazebo>

</robot>
C. Radar Xacro file
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <!-- <雷达> -->
    <!-- <
        1.支撑尺寸:高度 半径
        2.关节属性: x y z


        1.雷达尺寸:高度 半径
        2.关节属性: x y z
    > -->
    <xacro:property name="suport_radius" value="0.01"/>
    <xacro:property name="suport_length" value="0.15"/>
    <xacro:property name="suport_mass" value="0.10"/>

    <xacro:property name="joint_suport_x" value="0"/>
    <xacro:property name="joint_suport_y" value="0"/>
    <xacro:property name="joint_suport_z" value="${suport_length / 2+ base_length / 2 }"/>

    <xacro:property name="laser_radius" value="0.03"/>
    <xacro:property name="laser_length" value="0.05"/>
    <xacro:property name="laser_mass" value="0.15"/>

    <xacro:property name="joint_laser_x" value="0"/>
    <xacro:property name="joint_laser_y" value="0"/>
    <xacro:property name="joint_laser_z" value="${suport_length / 2+ laser_length / 2}"/>

    <link name="suport_link">
        <visual>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
            <geometry>
                <cylinder radius="${suport_radius}" length="${suport_length}"/>
            </geometry>
            <material name="suport_link">
                <color rgba="1.0 0.0 1.0 0.6"/>
            </material>
        </visual>
        <collision>
            <geometry>
                <cylinder radius="${suport_radius}" length="${suport_length}"/>
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
        </collision>
        <xacro:cylinder_inertial_matrix m="${suport_mass}" r="${suport_radius}" h="${suport_length}"/>
    </link>

    <joint name="suport2baselink" type="fixed">
        <parent link="base_link"/>
        <child link="suport_link"/>
        <origin xyz="${joint_suport_x} ${joint_suport_y} ${joint_suport_z}" rpy="0.0 0.0 0.0"/>
    </joint>
    <gazebo reference="suport_link">
        <material>
                Gazebo/Grey 
        </material>
    </gazebo>


    <link name="laser">
        <visual>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
            <geometry>
                <cylinder radius="${laser_radius}" length="${laser_length}"/>
            </geometry>
            <material name="laser">
                <color rgba="0.5 0.7 1.0 0.8"/>
            </material>
        </visual>
        <collision>
            <geometry>
                <cylinder radius="${laser_radius}" length="${laser_length}"/>
            </geometry>
            <origin xyz="0.0 0.0 0.0" rpy="0.0 0.0 0.0"/>
        </collision>
        <xacro:cylinder_inertial_matrix m="${laser_mass}" r="${laser_radius}" h="${laser_length}"/>
    </link>

    <joint name="laser2suportlink" type="fixed">
        <parent link="suport_link"/>
        <child link="laser"/>
        <origin xyz="${joint_laser_x} ${joint_laser_y} ${joint_laser_z}" rpy="0 0 0"/>
    </joint>
    <gazebo reference="laser">
        <material>
                Gazebo/Black 
        </material>
    </gazebo>


</robot>
D. Xacro file combining chassis, camera and radar
<?xml version="1.0"?>
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <xacro:include filename="inertia.xacro"/>

    <!-- <文件包含> -->

    <xacro:include filename="demo05_car_base.urdf.xacro"/>
    <xacro:include filename="demo06_car_camera.urdf.xacro"/>
    <xacro:include filename="demo07_car_laser.urdf.xacro"/>

</robot>

3. Execute in gazebo

launch file:

<launch>
    <!-- <需要在参数服务器中载入urdf> -->
    <param name="robot_description" command="$(find xacro)/xacro $(find urdf02_gazebo)/urdf/car.urdf.xacro" />
    <!-- <启动Gazebo仿真环境> -->
    <include file="$(find gazebo_ros)/launch/empty_world.launch">
        <arg name="world_name" value="$(find urdf02_gazebo)/worlds/box_house.world" />
    </include>
    <!-- <在Gazebo中添加机器人模型> -->
    <node pkg="gazebo_ros" type="spawn_model" name="model" args="-urdf -model mycar -param robot_description" />
</launch>

insert image description here

6.4 Gazebo simulation environment construction

There are two ways to create simulation implementations in Gazebo:

  • Method 1: Directly add built-in components to create a simulation environment
  • Method 2: Manually draw the simulation environment (more flexible)

You can also directly download and use official or third-party enhanced simulation environment plug-ins.

1. Add built-in components to create a simulation environment

1.1 Start Gazebo and add components

insert image description here

1.2 Save the simulation environment

insert image description here

After adding, select file —> Save World as to select the save path (under the function package: worlds directory), customize the file name, and set the suffix to .world

1.3 start
<launch>

    <!-- 将 Urdf 文件的内容加载到参数服务器 -->
    <param name="robot_description" command="$(find xacro)/xacro $(find demo02_urdf_gazebo)/urdf/xacro/my_base_camera_laser.urdf.xacro" />
    <!-- 启动 gazebo -->
    <include file="$(find gazebo_ros)/launch/empty_world.launch">
        <arg name="world_name" value="$(find demo02_urdf_gazebo)/worlds/hello.world" />
    </include>

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

argCore code: After starting empty_world, load the customized simulation environment according to

<include file="$(find gazebo_ros)/launch/empty_world.launch">
    <arg name="world_name" value="$(find demo02_urdf_gazebo)/worlds/hello.world" />
</include>
Copy

2. Customize the simulation environment

2.1 Start gazebo Open the construction panel and draw the simulation environment

insert image description here

2.2 Save the built environment

Click: file in the upper left corner —> Save (under the save path function package: models)

Then file —> Exit Building Editor

2.3 Save as world file

You can add some plug-ins like method 1, and then save it as a world file (under the save path function package: worlds)

insert image description here

2.4 start

same way 1

3. Use official plug-ins

At present, the simulation props provided by Gazebo are limited, and the official support can also be downloaded to provide more abundant simulation implementations. The specific implementations are as follows:

3.1 Download the official model library
git clone https://github.com/osrf/gazebo_models

Was: hg clone https://bitbucket.org/osrf/gazebo_modelsbut is no longer available

NOTE: This process may be time consuming

3.2 Copy the model library into gazebo

Copy the obtained gazebo_models folder contents to /usr/share/gazebo-*/models

3.3 Application

Restart Gazebo, select insert on the left menu bar to select and insert relevant props

7 Comprehensive application of URDF, Gazebo and Rviz

Simulate the robot's sensors through Gazebo, and then display the data perceived by these sensors in Rviz. The main contents include:

  • Motion control and odometer information display
  • Radar information simulation and display
  • Camera information simulation and display
  • kinect information simulation and display

7.1 Robot motion control and odometer information display

The robot model can be displayed normally in gazebo, so how to control the robot movement like in rviz? Here, the component in ros needs to be involved: ros_control.

1. Introduction to ros_control

**Scenario:** How to deploy the same set of ROS programs on different robot systems, for example: in the development stage, in order to improve efficiency, it is tested on the simulation platform, and when deployed, there are different physical robot platforms. The realization of different platforms is If there are differences, how to ensure the portability of ROS programs? ROS built-in solution is ros_control.

**ros_control:** is a set of packages that includes controller interface, controller manager, transport and hardware interface. ros_control is a set of middleware for robot control, which is a set of specifications. As long as different robot platforms are implemented according to this set of specifications, they can ensure compatibility with ROS programs. Through this set of specifications, a pluggable architecture design is realized. , greatly improving the efficiency and flexibility of program design.

Gazebo has implemented the related interface of ros_control, if you need to control the robot movement in gazebo, you can directly call the related interface

2. Motion control implementation process (Gazebo)

Inherited, the basic process of motion control:

  1. For the robot model that has been created, write a separate xacro file to add transmissions and controllers to the robot model
  2. Integrate this file into the xacro file
  3. Start Gazebo and issue /cmd_vel message to control robot movement
2.1 Add transmission and controller to joint

Two-wheel differential configuration

<robot name="my_car_move"
    xmlns:xacro="http://wiki.ros.org/xacro">

    <!-- 传动实现:用于连接控制器与关节 -->
    <xacro:macro name="joint_trans" params="joint_name">
        <!-- Transmission is important to link the joints and the controller -->
        <transmission name="${joint_name}_trans">
            <type>transmission_interface/SimpleTransmission</type>
            <joint name="${joint_name}">
                <hardwareInterface>hardware_interface/VelocityJointInterface</hardwareInterface>
            </joint>
            <actuator name="${joint_name}_motor">
                <hardwareInterface>hardware_interface/VelocityJointInterface</hardwareInterface>
                <mechanicalReduction>1</mechanicalReduction>
            </actuator>
        </transmission>
    </xacro:macro>

    <!-- 每一个驱动轮都需要配置传动装置 参考demo05 joint name ${name}2link    名字一定要打对,否则后续启动gazebo不会出现cmd_vel-->
    <xacro:joint_trans joint_name="left2link" />
    <xacro:joint_trans joint_name="right2link" />

    <!-- 控制器 -->
    <gazebo>
        <plugin name="differential_drive_controller" filename="libgazebo_ros_diff_drive.so">
            <rosDebugLevel>Debug</rosDebugLevel>
            <publishWheelTF>true</publishWheelTF>
            <robotNamespace>/</robotNamespace>
            <publishTf>1</publishTf>
            <publishWheelJointState>true</publishWheelJointState>
            <alwaysOn>true</alwaysOn>
            <updateRate>100.0</updateRate>
            <legacyMode>true</legacyMode>
            <leftJoint>left2link</leftJoint>            <!-- 左轮 -->
            <rightJoint>right2link</rightJoint>            <!-- 右轮 -->
            <wheelSeparation>${base_radius * 2}</wheelSeparation>            <!-- 车轮间距 -->
            <wheelDiameter>${wheel_radius * 2}</wheelDiameter>            <!-- 车轮直径 -->
            <broadcastTF>1</broadcastTF>
            <wheelTorque>30</wheelTorque>
            <wheelAcceleration>1.8</wheelAcceleration>
            <commandTopic>cmd_vel</commandTopic>            <!-- 运动控制话题 -->
            <odometryFrame>odom</odometryFrame>
            <odometryTopic>odom</odometryTopic>            <!-- 里程计话题 -->
            <robotBaseFrame>base_footprint</robotBaseFrame>            <!-- 根坐标系 -->
        </plugin>
    </gazebo>

</robot>

2.2 Add xacro file
<!-- 摄像头 -->
<robot name="my_sensors" xmlns:xacro="http://wiki.ros.org/xacro">
  <!-- 被引用的link -->
  <gazebo reference="camera">
    <!-- 类型设置为 camara -->
    <sensor type="camera" name="camera_node">
      <update_rate>30.0</update_rate> <!-- 更新频率 -->
      <!-- 摄像头基本信息设置 -->
      <camera name="head">
        <horizontal_fov>1.3962634</horizontal_fov>
        <image>
          <width>1280</width>
          <height>720</height>
          <format>R8G8B8</format>
        </image>
        <clip>
          <near>0.02</near>
          <far>300</far>
        </clip>
        <noise>
          <type>gaussian</type>
          <mean>0.0</mean>
          <stddev>0.007</stddev>
        </noise>
      </camera>
      <!-- 核心插件 -->
      <plugin name="gazebo_camera" filename="libgazebo_ros_camera.so">
        <alwaysOn>true</alwaysOn>
        <updateRate>0.0</updateRate>
        <cameraName>/camera</cameraName>
        <imageTopicName>image_raw</imageTopicName>
        <cameraInfoTopicName>camera_info</cameraInfoTopicName>
        <frameName>camera</frameName>
        <hackBaseline>0.07</hackBaseline>
        <distortionK1>0.0</distortionK1>
        <distortionK2>0.0</distortionK2>
        <distortionK3>0.0</distortionK3>
        <distortionT1>0.0</distortionT1>
        <distortionT2>0.0</distortionT2>
      </plugin>
    </sensor>
  </gazebo>
</robot>

<!-- kinetic -->
<robot name="my_sensors" xmlns:xacro="http://wiki.ros.org/xacro">
    <gazebo reference="suport_link">  
      <sensor type="depth" name="camera">
        <always_on>true</always_on>
        <update_rate>20.0</update_rate>
        <camera>
          <horizontal_fov>${60.0*PI/180.0}</horizontal_fov>
          <image>
            <format>R8G8B8</format>
            <width>640</width>
            <height>480</height>
          </image>
          <clip>
            <near>0.05</near>
            <far>8.0</far>
          </clip>
        </camera>
        <plugin name="kinect_camera_controller" filename="libgazebo_ros_openni_kinect.so">
          <cameraName>camera</cameraName>
          <alwaysOn>true</alwaysOn>
          <updateRate>10</updateRate>
          <imageTopicName>rgb/image_raw</imageTopicName>
          <depthImageTopicName>depth/image_raw</depthImageTopicName>
          <pointCloudTopicName>depth/points</pointCloudTopicName>
          <cameraInfoTopicName>rgb/camera_info</cameraInfoTopicName>
          <depthImageCameraInfoTopicName>depth/camera_info</depthImageCameraInfoTopicName>
          <frameName>support_depth</frameName>
          <baseline>0.1</baseline>
          <distortion_k1>0.0</distortion_k1>
          <distortion_k2>0.0</distortion_k2>
          <distortion_k3>0.0</distortion_k3>
          <distortion_t1>0.0</distortion_t1>
          <distortion_t2>0.0</distortion_t2>
          <pointCloudCutoff>0.4</pointCloudCutoff>
        </plugin>
      </sensor>
    </gazebo>

</robot>


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

  <!-- 雷达 -->
  <gazebo reference="laser"><!-- mingzi -->
    <sensor type="ray" name="rplidar">
      <pose>0 0 0 0 0 0</pose>
      <visualize>true</visualize>
      <update_rate>5.5</update_rate>
      <ray>
        <scan>
          <horizontal>
            <samples>360</samples>
            <resolution>1</resolution>
            <min_angle>-3</min_angle>
            <max_angle>3</max_angle>
          </horizontal>
        </scan>
        <range>
          <min>0.10</min>
          <max>30.0</max>
          <resolution>0.01</resolution>
        </range>
        <noise>
          <type>gaussian</type>
          <mean>0.0</mean>
          <stddev>0.01</stddev>
        </noise>
      </ray>
      <plugin name="gazebo_rplidar" filename="libgazebo_ros_laser.so">
        <topicName>/scan</topicName><!-- hua ti -->
        <frameName>laser</frameName><!-- leidazuobiaoxi -->
      </plugin>
    </sensor>
  </gazebo>
</robot>


2.3 xacro file integration

Finally, the above xacro file needs to be integrated into the overall robot model file. The code example is as follows:

<!-- 组合小车底盘与摄像头 -->
<?xml version="1.0"?>
<robot xmlns:xacro="http://www.ros.org/wiki/xacro" name="mycar">
    <xacro:include filename="inertia.xacro"/>

    <!-- <文件包含> -->


    <xacro:include filename="demo05_car_base.urdf.xacro"/>
    <xacro:include filename="demo06_car_camera.urdf.xacro"/>
    <xacro:include filename="demo07_car_laser.urdf.xacro"/>

    <xacro:include filename="gazebo/move.xacro"/>

    <xacro:include filename="gazebo/laser.xacro"/>
    <xacro:include filename="gazebo/camera.xacro"/>
    <xacro:include filename="gazebo/kinect.xacro"/>



</robot>

Current core: xacro file containing controller and drive configuration

<xacro:include filename="move.xacro" />
2.4 Start gazebo and control the robot movement

launch file:

<launch>
    <!-- <需要在参数服务器中载入urdf> -->
    <param name="robot_description" command="$(find xacro)/xacro $(find urdf02_gazebo)/urdf/car.urdf.xacro" />
    <!-- <启动Gazebo仿真环境> -->
    <include file="$(find gazebo_ros)/launch/empty_world.launch">
        <arg name="world_name" value="$(find urdf02_gazebo)/worlds/box_house.world" />
    </include>
    <!-- <在Gazebo中添加机器人模型> -->
    <node pkg="gazebo_ros" type="spawn_model" name="model" args="-urdf -model mycar -param robot_description" />
</launch>

Start the launch file, use the topic list to view the topic list, you will find that there are more /cmd_vel and then release the vmd_vel message control

Use command control (or you can write individual node control)

rostopic pub -r 10 /cmd_vel geometry_msgs/Twist '{linear: {x: 0.2, y: 0, z: 0}, angular: {x: 0, y: 0, z: 0.5}}'

The car is running normally in Gazebo

3. Rviz view odometer information

In Gazebo's simulation environment, the robot's odometer information and movement orientation cannot be obtained, and the robot's odometer information and movement orientation can be displayed through Rviz

Odometer: The pose state of the robot relative to the coordinate system of the starting point (X coordinate, Y coordinate, Z coordinate and orientation).

3.1 Start Rviz

launch file

<launch>

    <!-- 设置点云图tf变换参数 -->
    <node pkg="tf2_ros" type="static_transform_publisher" name="static_transform_publisher" args="0 0 0 -1.57 0 -1.57 /suport_link /support_depth" />

    <!-- 启动 rviz -->
    <node pkg="rviz" type="rviz" name="rviz" args="-d $(find urdf01_rviz)/config/show_mycar.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" />

</launch>
3.2 Add components

After executing the launch file, add the icon component in Rviz:

insert image description here

run:

roslaunch urdf02_gazebo demo03_env.launch 
roslaunch urdf02_gazebo demo04_sensor.launch 
rosrun teleop_twist_keyboard teleop_twist_keyboard.py _speed:=0.3 _turn:=0.5
rostopic pub -r 10 /cmd_vel geometry_msgs/Twist "linear:
  x: 0.0
  y: 0.0
  z: 0.0
angular:
  x: 0.0
  y: 0.0
  z: 0.3" 

Note: The name must be typed correctly, otherwise cmd_vel will not appear in the subsequent start of gazebo

8. Summary of this chapter

URDF is an xml file used to describe the robot model. Different tags can be used to represent different meanings. URDF writes robot model code redundancy. xacro can optimize URDF implementation, and the code implementation is more streamlined, efficient, and easy to read. It is easy to confuse Rviz and Gazebo. Here we focus on the differences between the following two:

rviz is a 3D visualization tool , emphasizing the visualization of existing data;

gazebo is a 3D physical simulation platform , emphasizing the creation of a virtual simulation environment.

rviz requires existing data .

rviz provides a lot of plug-ins, these plug-ins can display information such as images, models, paths, etc., but the premise is that these data have been released in the form of topics and parameters. What rviz does is to subscribe to these data and complete the visual rendering, so that the development It is easier for the reader to understand the meaning of the data.

Gazebo is not a display tool, it emphasizes simulation, it does not need data, but creates data .

We can create a robot world in gazebo for free, which can not only simulate the motion function of the robot, but also simulate the sensor data of the robot. And these data can be displayed in rviz, so when using gazebo, it is often used in conjunction with rviz. When we do not have robot hardware or the experimental environment is difficult to build, simulation is often a very useful tool.

To sum up, if you already have a robot hardware platform and can complete the required functions on it, using rviz should be able to meet the development needs.

If you don't have robot hardware, or want to do some algorithm and application tests in a simulation environment, gazebo+rviz should be what you need.

In addition, rviz can also create a simple simulation environment with other function packages, such as rviz+ArbotiX.

Guess you like

Origin blog.csdn.net/TianHW103/article/details/128191905