如何将机器人变成游戏控制器
如果机器人能变成一个游戏控制器会怎样?
在这个项目中,我们将把一个简单的双自由度机械臂连接到Unity游戏中,并利用机械臂来操控游戏中的内容。
我们将使用ESP32-WROOM-32和两个5k电阻电位器来模拟机械臂的两个关节。ESP32读取关节位置,并通过USB串口将数据发送给Unity。
Unity随后使用正向运动学技术,在游戏中重建机械臂的动作。
当所有系统正常运行后,我们将把虚拟机械臂转变为一个简易的游戏控制器,并加入物理反馈。我们还将探讨如何使用ROS-TCP-Endpoint集成ROS 2,以便将游戏连接到更复杂的机器人系统。
你不需要ROS 2也能跟随主教程。
我们正在构建的内容
基本思路非常简单:当你移动机械臂时,虚拟手臂随之移动,而虚拟手臂可以与游戏进行交互。
在本项目中,我们使用了两个电位器,而不是完整的机械臂。这使得硬件保持简单,同时仍能提供与真实机器人相同的基本关节位置数据。
工作原理
该项目主要包含三个部分。
•ESP32 读取物理关节的位置,并将数据发送到计算机。
•Unity 接收这些位置信息,计算虚拟机器人的位置,并运行游戏。
•ROS 2 是可选的。如果之后添加它,将为 Unity 提供与其他机器人软件通信的方式。
1. 构建物理控制器
我们将使用两个5k的电位器来模拟一个两自由度机械臂的两个关节,其中电位器1和电位器2分别对应关节1和关节2。
实际机器人可以使用编码器或其他位置传感器来替代。对于本项目,电位器是一种廉价且简便的方法,用于生成类似类型的关节位置数据。
我们所建模的机械臂是一个简单的两连杆系统,大致如下所示:
第一个电位器提供theta1,第二个电位器提供theta2。
2. 连接电位器
每个电位器有三个接线端:3.3V、GND 和滑块(Wiper)。我们可以按照电路图所示进行连接,使用 GPIO 34 和 35 连接滑块。
请确保电位器连接到 3.3V,而不是 5V。
3. 编程ESP32
ESP32的任务相当简单:它读取两个电位器的值,将这些值转换为角度,并将角度发送给Unity。
我们将以以下格式发送:
例如:
以下是Arduino代码:
-90到90度的范围只是一个示例。实际得到的范围取决于电位器的安装方式,因此您可能需要调整这些数值:
4. 检查 ESP32 输出
上传代码并打开 Arduino 串口监视器。
将波特率设置为 115200。
你应该能看到类似以下内容:
转动第一个电位器,检查第一个数字是否发生变化。
然后转动第二个电位器,检查第二个数字是否发生变化。
如果一切正常,说明硬件部分已准备就绪。
5. 在 Unity 中创建虚拟机器人
现在,我们将用 Unity 构建一个相同机械臂的简化版本。
你不需要复杂的机器人模型,这个项目只需要两个矩形 GameObject 就足够了。
关键在于正确设置层级关系和关节点。
一个简单的层级结构可以是:
具体外观由你决定。重要的是,Link 1 围绕 Joint 1 旋转,Link 2 围绕 Joint 2 旋转。
例如,我们使用:
Unity的尺寸不必与物理手臂完全一致,我们只需要相同的两个连杆基本几何结构即可。
6. 将Unity连接到ESP32
当ESP32通过USB连接时,Windows会为其分配一个COM端口。
Unity可以使用C#读取该端口。
创建
一个名为SerialReader.cs的脚本,并将其分配给一个游戏对象:
将以下内容修改为你的ESP32所使用的COM端口号。
你可以在Windows设备管理器或Arduino IDE中找到这个端口。
在运行Unity场景之前,请确保关闭Arduino串口监视器。当串口监视器打开时,它会占用COM端口的控制权,导致Unity无法访问该端口。
7. 添加正向运动学
现在进入机器人部分。
ESP32 提供了两个关节角度,但 Unity 还需要确定机械臂末端的位置。这时就需要使用正向运动学。
对于我们的双连杆机械臂,末端执行器的位置为:
简单来说:
我们已知两个关节角度,因此可以计算出机械臂末端应处于的位置。
Unity 在使用三角函数时期望输入的角度单位为弧度,所以我们需要先将传入的度数转换为弧度。
创建 RobotKinematics.cs 文件,并将其赋值给任意 GameObject:
8. 让虚拟手臂跟随
我们还需要旋转连接件本身。
第一个连接件跟随 theta1,第二个连接件跟随 theta1 + theta2。
移动第一个电位器,第一个关节应该随之移动。移动第二个电位器,第二个关节应相对于第一个关节移动。
一旦实现这一点,我们就成功地将一个物理输入设备连接到了虚拟机器人上。
9. 将机器人变成游戏控制器
这时事情变得更加有趣了。我们不再只是观察虚拟机械臂的运动,而是可以赋予它一些任务。例如“触达目标”。
在机器人的工作区域内创建一个目标。玩家需要手动移动机械臂,直到虚拟末端执行器到达该目标。
当末端执行器触达目标时:目标达成 → 得分+1 → 进入下一个目标
10. 发送反馈 返回机器人
到目前为止,所有数据都是从机器人传送到Unity的:但我们也可以反过来——从Unity传回机器人。
例如,当玩家到达目标时,Unity可以向ESP32发送TARGET_REACHED信号。
ESP32随后可以开启LED或激活其他输出,从而形成一个完整的反馈回路:
这在虚拟环境需要向机器人使用者提供反馈的应用中非常有用。
11. 如果我们使用一个真正的机器人会怎样?
这种设置的好处在于,电位器并不是真正关键的部分,它们只是提供关节的角度信息。
在真正的机器人上,我们可以用旋转编码器、磁编码器、电机位置反馈或其他关节位置传感器来替代它们。
12. 可选:添加 ROS 2
虽然本教程中为可选内容,但我们的架构支持在不牺牲其他功能的前提下集成 ROS。当您希望 Unity 与其他机器人软件进行通信时,ROS 就变得非常有用。
ROS-TCP-Endpoint 是 Unity Technologies 提供的一款免费工具,可在 Unity 与 ROS 2 之间建立连接点。您可以将该工具克隆到 ROS 工作空间中,并在单独的终端中运行,以便当需要 ROS 2 节点与 Unity 交换数据时使用。一旦连接建立,Unity 和 ROS 2 之间就可以传输诸如机器人关节角度等信息。
随后,ROS 2 节点可以订阅这些数据,并用于多种应用。无论是简单地显示关节数值,还是复杂地将其用于机器人控制器、AI 系统或数据处理流程,均可实现。
Unity 无法打开串口
请检查以下内容:
- ESP32 已正确连接。
- 已选择正确的 COM 端口。
- Unity 正在使用 115200 波特率。
- Arduino 串口监视器已关闭。
- 没有其他应用程序正在使用该端口。
数值未发生变化
请先检查 Arduino 串口监视器。如果数值没有变化,问题出在ESP32或接线方面。如果数值正常变化,请检查Unity的COM端口和串口读取器。
虚拟机械臂移动异常
请检查:
- 潜伏电位器的角度限制;
- 各关节的方向;
- 链节长度;
- Unity的枢轴位置;
- 第二个关节是否使用了theta1 + theta2。
物理机械臂与虚拟机械臂未对齐
物理和Unity坐标系的原点位置或方向可能不同。
您可能需要添加一个偏移量:
在将物理机制的测量数据传输到虚拟环境时,这种情况是正常的。
结论
我们使用ESP32和USB串行通信,将一个物理的双自由度机器人接口连接到了Unity。
通过物理关节角度来重建具有正向运动学的虚拟机器人,从而使物理机器人能够充当游戏控制器。
随后,我们加入了双向通信功能,使游戏可以将反馈信息发送回物理系统。
最后,我们展示了当项目需要与更大规模的机器人系统通信时,如何集成ROS 2。
两个电位器可替换为真实的机器人关节传感器,这意味着从简单的原型到实际机器人平台,都可以采用相同的底层接口。
本文编译自hackster.io





