You're reading the documentation for a development version. For the latest released version, please have a look at Galactic.

理解 ROS 2 的行为

目标:在 ROS2 中的自省行为。

Tutorial level: Beginner

Time: 15 minutes

背景

动作是 ROS 2 中的通信类型之一,用于长时间运行的任务。它们由三个部分组成:目标、反馈和结果。

动作建立在主题和服务之上。它们的功能与服务类似,只是可以取消动作。它们还提供稳定的反馈,而不是只提供单一响应的服务。

动作使用客户端-服务器模型,类似于发布者-订阅者模型(在 主题 教程中描述)。“动作客户端”节点将目标发送到“动作服务器”节点,该节点确认目标并返回流和结果。

../_images/Action-SingleActionClient.gif

先决条件

本教程建立在一些概念之上,如 节点主题,在以前的教程中涉及。

本教程使用 turtlesim 软件包

像往常一样,不要忘记在 你打开的每一个新终端 中为 ROS 2 激活源码。

任务

1 设置

启动两个 turtlesim 节点 /turtlesim/teleop_turtle

打开一个新的终端并运行:

ros2 run turtlesim turtlesim_node

打开另一个终端并运行:

ros2 run turtlesim turtle_teleop_key

2 使用动作

当您启动 /teleop_turtle 节点时,您将在终端中看到以下消息:

Use arrow keys to move the turtle.
Use G|B|V|C|D|E|R|T keys to rotate to absolute orientations. 'F' to cancel a rotation.

让我们关注第二行,它对应一个动作。(第一个指令对应于前面在 主题教程 中讨论的“cmd_vel”主题。)

注意,字母键 G|B|V|C|D|E|R|T 在 US QWERTY 键盘上的 F 键周围形成一个“框”(如果你没有使用 QWERTY 键盘,请参阅下面的 链接)。每个键在 F 周围的位置对应于 turtlesim 中的那个方向。例如,E 会将海龟的方向旋转到左上角。

请注意 /turtlesim 节点运行的终端。每当您按下这些键之一时,您就向 /turtlesim 节点的动作服务器发送一个目标。目标是旋转海龟朝向特定的方向。一旦海龟完成了它的旋转,就会显示一个传递目标结果的消息:

[INFO] [turtlesim]: Rotation goal completed successfully

F 键将在执行过程中取消目标。

尝试按下 C 键,然后在海龟完成旋转之前按下 F 键。在 /turtlesim 节点运行的终端中,你会看到这样的消息:

[INFO] [turtlesim]: Rotation goal canceled

不仅客户端(您在 teleop 中的输入)可以停止目标,服务器端(/turtlesim 节点)也可以。当服务器端选择停止处理一个目标时,它被称为“中止”(abort)该目标。

试着按下 D 键,然后在第一次旋转完成之前按下 G 键。在 /turtlesim 节点运行的终端中,你会看到这样的消息:

[WARN] [turtlesim]: Rotation goal received before a previous goal finished. Aborting previous goal

这个动作服务器选择中止第一个目标,因为它有了一个新的目标。它可以选择其他的目标,比如拒绝新的目标,或者在第一个目标完成后执行第二个目标。不要假设每个动作服务器在获得一个新目标时都会选择中止当前目标。

3 ros2 node info

要查看 /turtlesim 节点的动作,打开一个新的终端并运行命令:

ros2 node info /turtlesim

它将返回 /turtlesim 的订阅者、发布者、服务、动作服务器和动作客户端列表:

/turtlesim
  Subscribers:
    /parameter_events: rcl_interfaces/msg/ParameterEvent
    /turtle1/cmd_vel: geometry_msgs/msg/Twist
  Publishers:
    /parameter_events: rcl_interfaces/msg/ParameterEvent
    /rosout: rcl_interfaces/msg/Log
    /turtle1/color_sensor: turtlesim/msg/Color
    /turtle1/pose: turtlesim/msg/Pose
  Service Servers:
    /clear: std_srvs/srv/Empty
    /kill: turtlesim/srv/Kill
    /reset: std_srvs/srv/Empty
    /spawn: turtlesim/srv/Spawn
    /turtle1/set_pen: turtlesim/srv/SetPen
    /turtle1/teleport_absolute: turtlesim/srv/TeleportAbsolute
    /turtle1/teleport_relative: turtlesim/srv/TeleportRelative
    /turtlesim/describe_parameters: rcl_interfaces/srv/DescribeParameters
    /turtlesim/get_parameter_types: rcl_interfaces/srv/GetParameterTypes
    /turtlesim/get_parameters: rcl_interfaces/srv/GetParameters
    /turtlesim/list_parameters: rcl_interfaces/srv/ListParameters
    /turtlesim/set_parameters: rcl_interfaces/srv/SetParameters
    /turtlesim/set_parameters_atomically: rcl_interfaces/srv/SetParametersAtomically
  Service Clients:

  Action Servers:
    /turtle1/rotate_absolute: turtlesim/action/RotateAbsolute
  Action Clients:

注意 /turtlesim/turtle1/rotate_absolute 操作位于 Action Servers 下。这意味着 /turtlesim 响应 /turtle1/rotate_absolute 动作并提供反馈。

/teleop_turtle 节点在 Action Clients 下的名称为 /turtle1/rotate_absolute,这意味着它发送该操作名称的目标。

ros2 node info /teleop_turtle

这将返回:

/teleop_turtle
  Subscribers:
    /parameter_events: rcl_interfaces/msg/ParameterEvent
  Publishers:
    /parameter_events: rcl_interfaces/msg/ParameterEvent
    /rosout: rcl_interfaces/msg/Log
    /turtle1/cmd_vel: geometry_msgs/msg/Twist
  Service Servers:
    /teleop_turtle/describe_parameters: rcl_interfaces/srv/DescribeParameters
    /teleop_turtle/get_parameter_types: rcl_interfaces/srv/GetParameterTypes
    /teleop_turtle/get_parameters: rcl_interfaces/srv/GetParameters
    /teleop_turtle/list_parameters: rcl_interfaces/srv/ListParameters
    /teleop_turtle/set_parameters: rcl_interfaces/srv/SetParameters
    /teleop_turtle/set_parameters_atomically: rcl_interfaces/srv/SetParametersAtomically
  Service Clients:

  Action Servers:

  Action Clients:
    /turtle1/rotate_absolute: turtlesim/action/RotateAbsolute

4 ros2 action list

要在 ROS graph 中识别所有的动作,运行命令:

ros2 action list

这将返回:

/turtle1/rotate_absolute

这是目前在 ROS graph 中唯一的动作。正如您前面看到的,它控制海龟的旋转。您还知道,通过使用 ros2 node info <node_name> 命令,这个动作有一个动作客户端(/teleop_turtle 的一部分)和一个动作服务器(/turtlesim 的一部分)。

4.1 ros2 action list -t

动作有类型,类似于主题和服务。要查找 /turtle1/rotate_absolute 的类型,运行命令:

ros2 action list -t

这将返回:

/turtle1/rotate_absolute [turtlesim/action/RotateAbsolute]

在每个动作名称右边的括号中(在本例中只有 /turtle1/rotate_absolute)是动作类型 turtlesim/action/RotateAbsolute。当您想从命令行或代码中执行操作时,您将需要这个。

5 ros2 action info

你可以使用以下命令来进一步反省 /turtle1/rotate_absolute 动作:

ros2 action info /turtle1/rotate_absolute

这将返回:

Action: /turtle1/rotate_absolute
Action clients: 1
    /teleop_turtle
Action servers: 1
    /turtlesim

这告诉我们前面在每个节点上运行 ros2 node info 时学到的内容:/teleop_turtle 节点有一个动作客户端,/turtlesim 节点有一个动作服务器,用于 /turtle1/rotate_absolute 动作。

6 ros2 interface show

在你自己发送或执行动作目标之前,你还需要了解动作类型的结构。

回想一下,在运行命令 ros2 action list -t 时,您确定了 /turtle1/rotate_absolute 的类型。在终端中输入以下命令,动作类型如下:

ros2 interface show turtlesim/action/RotateAbsolute

这将返回:

# The desired heading in radians
float32 theta
---
# The angular displacement in radians to the starting position
float32 delta
---
# The remaining rotation in radians
float32 remaining

该消息的第一部分,在 --- 之上,是目标请求的结构(数据类型和名称)。下一部分是结果的结构。最后一部分是反馈的结构。

7 ros2 action send_goal

现在让我们用下面的语法从命令行发送一个动作目标:

ros2 action send_goal <action_name> <action_type> <values>

<values> 需要为 YAML 格式。

注意 turtlesim 窗口,并在终端中输入以下命令:

ros2 action send_goal /turtle1/rotate_absolute turtlesim/action/RotateAbsolute "{theta: 1.57}"

你应该看到海龟在旋转,在你的终端中还会看到以下消息:

Waiting for an action server to become available...
Sending goal:
   theta: 1.57

Goal accepted with ID: f8db8f44410849eaa93d3feb747dd444

Result:
  delta: -1.568000316619873

Goal finished with status: SUCCEEDED

所有目标都有一个唯一的 ID,显示在返回消息中。您还可以看到结果,一个名为 delta 的字段,这是到起始位置的位移。

要查看这个目标的反馈,在 ros2 action send_goal 命令中添加 --feedback

ros2 action send_goal /turtle1/rotate_absolute turtlesim/action/RotateAbsolute "{theta: -1.57}" --feedback

您的终端将返回消息:

Sending goal:
   theta: -1.57

Goal accepted with ID: e6092c831f994afda92f0086f220da27

Feedback:
  remaining: -3.1268222332000732

Feedback:
  remaining: -3.1108222007751465



Result:
  delta: 3.1200008392333984

Goal finished with status: SUCCEEDED

你将继续收到反馈,remaining 弧度,直到目标完成。

小结

动作类似于服务,允许您执行长时间运行的任务,提供定期反馈,并且是可取消的。

机器人系统很可能使用动作来导航。动作目标可以告诉机器人移动到某个位置。当机器人导航到某个位置时,它可以在沿途发送更新(即反馈),然后在到达目的地后发送最终结果信息。

Turtlesim 有一个动作服务器,动作客户端可以向其发送目标来旋转海龟。在本教程中,您自省了 /turtle1/rotate_absolute 动作,以便更好地了解什么动作。

下一步

现在你已经涵盖了所有的 ROS 2 核心概念。这套教程中的最后几个教程将向你介绍一些工具和技术,使你更容易使用 ROS 2,从 使用 rqt_console 开始。”