# Roby 状态机如何按端口条件切换状态

> 原文链接：https://robotics.hellobike.com/pitfalls/2014-06-11-robotics-se-3049
> 频道：pitfalls | 更新日期：2014-06-11 | 标签：auto, stackexchange, rock, syskit
> 核心摘要：在 Roby/Syskit 中不要直接条件化 forward，应通过专用 composition 或 task_script 监控端口后发事件。

# Roby 状态机如何按端口条件切换状态

::: v-pre
> 本文由 AI 根据公开内容整理，可能有误，请以原文为准：[How to define conditions for state-machines in roby?](https://robotics.stackexchange.com/questions/3049/how-to-define-conditions-for-state-machines-in-roby)（Robotics Stack Exchange #3049）

**状态**：已解决

## 问题

提问者想在 AUV 开始 pipeline-tracking 前检查当前航向，确保对准正确管线，并希望对状态机中的 `forward pipe_detector.align_auv_event, success_event` 增加端口条件。

## 环境

Linux / ROS 机器人软件与控制通用开发环境

## 解决办法

1. 不建议在状态机里直接对 `forward` 加条件；原文称旧版曾有此能力，但因复杂度高已移除。
2. 创建专用 `Syskit::Composition`，加入 `PipelineDetector::Task`，定义 `expected_heading` 参数和 `heading_within_tolerance?` 判断。
3. 在 `task_script` 中创建相关端口 reader，等待 `detector.align_auv_event`，用 `read_new` 读取数据并检查 `data.yaw` 是否在容差内。
4. 条件满足则 `emit :success`，否则 `emit :false_positive`；也可在单独 action 中把同样的 `task_script` 挂到 detector 任务上。

原问题作者：Matthias Goldhoorn；采纳答案作者：sylvain.joyeux。原内容依 CC BY-SA 4.0 授权，本页摘要同样依 CC BY-SA 4.0 授权。
:::

## 原始参考来源 (Sources)

- [Robotics Stack Exchange #3049：How to define conditions for state-machines in roby?](https://robotics.stackexchange.com/questions/3049/how-to-define-conditions-for-state-machines-in-roby)