# Add a New Robot This project uses a simple adapter + behavior pattern. ## 1) Create a robot adapter Implement the common command interface: - File: `dora_voice_control/dora_voice_control/robots//adapter.py` - Base class: `RobotAdapter` (`dora_voice_control/dora_voice_control/core/robot.py`) Example (vacuum style): ```python from __future__ import annotations from typing import Any, Dict, List from ...core.robot import RobotAdapter from ...core.state import RobotStep NAME = "my_robot" ALIASES = {"my_robot", "my_alias"} class MyRobotAdapter(RobotAdapter): def grab(self) -> List[RobotStep]: return [RobotStep(action="vacuum_on", payload={})] def release(self) -> List[RobotStep]: return [RobotStep(action="vacuum_off", payload={})] def move(self, payload: Dict[str, Any]) -> List[RobotStep]: return [RobotStep(action="move_to_pose", payload=payload)] def reset_tool(self) -> List[RobotStep]: return [RobotStep(action="vacuum_off", payload={})] ``` The `action` strings must match what your robot node understands. ## 2) Create robot actions - File: `dora_voice_control/dora_voice_control/robots//actions.py` - Use `ActionInfo` to define names, aliases, and requirements. ```python from ...core.behavior import ActionInfo MY_ACTIONS = { "tomar": ActionInfo(name="tomar", aliases=["toma"], requires_object=False), "soltar": ActionInfo(name="soltar", aliases=["suelta"], requires_object=False), } ``` ## 3) Create robot behavior - File: `dora_voice_control/dora_voice_control/robots//behavior.py` - Subclass `RobotBehavior` and implement `action_handlers()`. ```python from typing import Callable from ...core.behavior import ActionContext, RobotBehavior from .actions import MY_ACTIONS class MyRobotBehavior(RobotBehavior): ACTIONS = MY_ACTIONS def action_tomar(self, ctx: ActionContext) -> bool: self._queue_steps(ctx, self.robot_adapter.grab()) return True def action_soltar(self, ctx: ActionContext) -> bool: self._queue_steps(ctx, self.robot_adapter.release()) return True def action_handlers(self) -> dict[str, Callable[[ActionContext], bool]]: return { "tomar": self.action_tomar, "soltar": self.action_soltar, } ``` ## 4) Register the robot - File: `dora_voice_control/dora_voice_control/robots/__init__.py` Add a resolver entry that maps `ROBOT_TYPE` to your adapter/behavior. ## 5) Update dataflow Set `ROBOT_TYPE` in your dataflow: ```yaml env: ROBOT_TYPE: "my_robot" ``` ## Safety notes - Keep bounds checks in behavior methods (`_queue_move` already checks workspace limits). - For real hardware, validate with a staged plan: simulation → dry-run → full run.