_images/robomaster.jpg

欢迎来到 RoboMaster 开发者页面

开篇介绍

EP套装介绍

RoboMaster EP 教育拓展套装在机甲大师 S1 教育机器人的基础上延展出丰富的拓展性,配有完善的课程内容及全新 RoboMaster 青少年专属赛事;各类编程模块均围绕教学需求精心设计,带来焕然一新的教学与学习体验,拓展未来教育的全新边界。

EP机器人形态

RoboMaster EP 教育套装可以组装出步兵机器人或工程机器人。其中步兵机器人在外观上与常规版本的 S1 较为接近,并在软硬件上还进行了升级,增加了许多新部件, 尤其是在拓展能力方面,升级后的机器人能够通过传感器转接模块接入第三方传感器,拥有更多的可编程空间。

alternate text

步兵机器人

工程机器人在 S1 的基础上做了较大的改动:使用一个并联机械臂代替了安装在底盘正中央的云台结构,保留了图传系统,并且在末端装配了一个机械夹爪,从而可以执行更加复杂的任务。在底盘的行动能力和整机的拓展能力上,则与步兵机器人有着同样高水准。

alternate text

工程机器人

网站内容

RoboMaster EP 作为一款教育机器人,具有强大的扩展性和可编程性,为了方便用户编程使用,官方 App 集成了 Scratch 编程,Python 编程的功能,并提供了跟第三方平台通信的明文 SDK 功能。

本网站为 RoboMaster EP 的技术开发网站,面向对象为使用 RoboMaster EP 的学生,教师和科技爱好者,为用户提供技术上的指引,方便对 RoboMaster EP 进行二次开发,扩展更加丰富的功能,解锁更多乐趣。

本网站分为四部分,主要内容介绍如下:

  • 快速开始
    对 RoboMaster EP 和本网站内容做了主要介绍,并提供了编程环境的安装方法,另外还介绍了 RoboMaster EP 如何跟第三方平台进行通信,扩展更加丰富的功能。
  • 扩展模块/扩展接口说明
    RoboMaster EP 相比 S1 有了更加丰富的扩展模块与拓展接口,这里对拓展模块以及拓展接口的配置和使用方法做以简单的说明。
  • 明文 SDK 说明
    用户使用第三方平台跟 RoboMaster EP 建立连接后,通过明文 SDK 对 EP 机器人进行更复杂更有趣的操作。本章对明文 SDK 的功能,用法和相关协议做了详细说明。
  • Python 编程说明
    本章主要介绍用户如何通过 RoboMaster EP 官方 App 内置的 python 编程环境对 EP 上新增的功能和模块进行编程,扩展更多玩法。
  • 示例程序
    本章主要提供一些示例程序,方便大家参考学习。
  • 版本说明
    本章主要描述了文档与机器人之间相互匹配的版本信息。

联系我们

如果您对该文档任何的建议和意见,欢迎在 RoboMaster-SDK Github 上联系我们。

编程环境安装

介绍

用户在 PC 上通过 WIFI、 USB 和 UART 跟 EP 建立连接后,可以使用明文 SDK 跟 EP 进行通信,进行更复杂的二次开发。在PC 上用户可以使用 C++、 C#、 Python 或是其他语言进行编程,这个可以按照用户开发能力自行决定。

为了让用户尽快熟悉 EP 的各个模块和功能,并方便使用本网站中的 Python 示例代码,我们介绍一下 Python 在 PC 上的安装步骤。

Windows 安装 Python

环境: Windows 10 64 位,Python 3.6.4

  1. python 官网上 找到 3.6.4 的安装包,选择下载文件进行下载。
_images/win10_python_setup1.png
  1. 双击下载好的安装文件,然后“下一步”就可以,需要注意的是我们选择自定义安装并勾选自动添加环境变量。
_images/win10_python_setup3.png
  1. 接着“下一步”,手动选择安装路径。
_images/win10_python_setup4.png
  1. 安装完成后按 win+r 输入 cmd 打开命令提示符界面,在命令行里面输入 python -V, 确认 Python 3.6 安装成功。

Ubuntu 安装 Python

环境: ubuntu 16.04 64 位,Python 3.6.3

  1. Ubuntu16.04 默认安装了Python2.7和3.5,请注意,系统自带的python千万不能卸载。输入命令 python -V,可以查看 Python 默认版本。
  2. 输入如下命令安装 python 3.6 软件包:
sudo add-apt-repository ppa:jonathonf/python-3.6
sudo apt-get update
sudo apt-get install python3.6
  1. 调整 Python3 的优先级,使得 Python 3.6 优先级较高。
sudo update-alternatives --install /usr/bin/python3 python3 /usr/bin/python3.5 1
sudo update-alternatives --install /usr/bin/python3 python3 /usr/bin/python3.6 2
sudo update-alternatives --install /usr/bin/python python /usr/bin/python2 100
sudo update-alternatives --install /usr/bin/python python /usr/bin/python3 150
  1. 此时再输入命令 python -V ,确认 Python 3.6 安装成功。

第三方平台通信

介绍

用户使用第三方平台跟 RoboMaster EP 建立连接后,通过明文 SDK 和 EP 机器人进行通信,可以控制各个内置模块和拓展模块,并获取 EP 机器人的视频流、音频流,极大的丰富了 EP 的扩展性,提供更多玩法。

第三方平台类型

用户使用的第三方平台为有自主计算能力,具有 WIFI 、 USB 和 UART 接口的计算平台。包括但不限于 DJI 妙算、Arduino 开发板、Micro:bit、树莓派、Jetson Nano 和 PC。

_images/third_part.png

通信方式

第三方平台和 RoboMaster EP 的通信方式包括三种: WIFI、 USB 和 UART。下面介绍这三种通信方式的连接方法。

WIFI 连接

WIFI 连接包括直连模式和路由器模式,具体参考如下说明。

直连模式
条件:

第三方平台具有 WIFI 连接功能。

用途:

第三方平台用 WIFI 连接到 EP 后,通过明文 SDK 和 EP 进行通信。

步骤:
  1. 启动 EP,切换智能中控的连接模式开关至 直连模式
  2. 打开第三方平台的无线网络,扫描 EP 的热点,进行连接。
  3. 通过明文 SDK 和 EP 进行通信。(参考 WIFI 直连模式)
应用举例:

DJI 妙算使用 WIFI 连接到 EP 后,通过明文 SDK 和 EP 进行通信,并获取 EP 的视频流、音频流。

示意图:
_images/wifi_direct.png

DJI 妙算、Jetson Nano 和 PC 通过 WIFI 直连模式连接到 EP

路由器模式
条件:

第三方平台具有 WIFI 或有线网络连接功能。

用途:

第三方平台和 EP 连接到同一个局域网中,通过明文 SDK 和 EP 进行通信。

步骤:
  1. 启动 EP,切换智能中控的连接模式开关 路由器模式
  2. 通过官方 App 的扫码连接方式将 EP 连接到路由器。
  3. 第三方平台通过 WIFI 或有线网络连接到同一路由器。
  4. 通过官方 App 的设置页面或是编写脚本等方式获取到 EP 的 IP 地址。
  5. 通过明文 SDK 和 EP 进行通信。(示例参考 WIFI 路由器模式)
应用举例:

PC 和 EP 连接到同一个局域网后,通过明文 SDK 和 EP 进行通信,并获取 EP 的视频流、音频流。

示意图:
_images/wifi_sta.png

DJI 妙算、Jetson Nano 和 PC 通过 WIFI 路由器模式连接到 EP

USB 连接

条件:

第三方平台具有 TypeA USB 接口,并支持 RNDIS 功能。

用途:

第三方平台通过 USB 线连接到 EP 的智能中控的 Micro USB 端口,使用明文 SDK 和 EP 进行通信。

步骤:
  1. 启动 EP,无需关心智能中控的连接模式开关位置。
  2. 第三方平台通过 USB 线连接到 EP 的智能中控。
  3. 通过明文 SDK 和 EP 进行通信。(示例参考 USB 连接)
应用举例:

Jetson Nano 固定在 EP 小车上,并由 EP 的电源转接模块供电,通过 USB 连接到 EP,使用明文 SDK 和 EP 进行通信,并获取 EP 的视频流、音频流。

示意图:
_images/raspberry.png

树莓派连接示意图

_images/nano.png

Jetson Nano连接示意图

UART 连接

条件:

第三方平台具有 UART 接口或有串口转 USB 功能。

用途:

第三方平台通过 UART 连接到 EP 运动控制器的 UART 接口,使用明文 SDK 和 EP 进行通信。

步骤:
  1. 启动 EP,无需关心智能中控的连接模式开关位置。
  2. 第三方平台 UART 的 TX/RX 和 GND 分别连接到 EP 运动控制器 UART 的 RX/TX 和 GND。(参考 引脚说明)
  3. 通过明文 SDK 和 EP 进行通信。(示例参考 UART 连接)
应用举例:

Arduino 固定在 EP 小车上,并由 EP 的电源转接模块供电,通过 UART 连接到 EP 运动控制器,使用明文 SDK 和 EP 进行通信。

示意图:
_images/arduino.jpg

Arduino连接示意图

_images/microbit.png

Micro:bit连接示意图

机械臂与机械爪

介绍

机械臂支持 FPV 精准遥控,机械爪配合机械臂使用,支持夹力控制,用户可在 App 中通过第一人称视角操控机械臂和机械爪完成任务。

_images/arm&gripper.png

使用说明

当机械臂或机械爪处于工作状态时,请尽量避免对其施加外力。 用户可以控制机械臂的移动范围、机械爪的开合距离。其中,机械臂的水平移动范围为 0-0.22 米,垂直移动范围为 0-0.15 米;机械爪的开合距离约为 10 厘米。

警告

1.请勿碰撞或损伤机械臂或机械爪,避免导致性能下降或舵机运行异常。

2.避免因用身体部位接触机械臂或机械爪旋转或尖锐部分而导致受伤。

3.及时清理水滴、水晶弹残渣等异物,避免腐蚀结构表面腐蚀。

机械爪PWM 接口说明:

机械爪支持力矩控制模式

_images/arm_pwm.png
序号 引脚
1 485A/PWM
2 485B
3 VCC-12V
4 GND

PWM 信号为50Hz,占空比为2.5%~12.5%。

  1. 2.5%~7.5% 占空比对应闭合力度[ 最大,0];
  2. 7.5%~12.5% 占空比对应开合力度[0,最大]。

Python API

请参考 机械臂 机械爪

舵机

介绍

舵机的油门控制方式除了支持 485 控制,还可以进行 PWM 控制,控制模式包含:速度模式和角度模式。

注解

舵机的控制模式

舵机的控制模式需要通过官方的编程接口( Scratch / Python )进行切换,并且会记录在舵机内部,不会随着舵机掉电而重置。使用 PWM 控制前请确认舵机当前的控制模式。

引脚说明

舵机上的 485 管脚和 PWM 管脚复用,如下图所示

_images/arm_pwm.png
序号 引脚
1 485A/PWM
2 485B
3 VCC-12V
4 GND

控制说明

在 PWM 控制方式下,舵机对应的输入输出

控制模式 脉冲周期 油门范围 舵机输出
角度模式 50Hz 2.5%~12.5% 0°~360°
速度模式 50hz 2.5%~7.5% 49rpm~0rpm,顺时针
7.5%~12.5% 0rpm~—49rpm,逆时针

Python API

请参考 舵机

红外深度传感器

介绍

红外深度传感器的设计是基于 TOF(Time of Flight)即飞行时间原理。即传感器发出经调制的近红外光,遇物体后反射,传感器通过计算光线发射和反射时间差或相位差,来计算距离物体的距离。

产品特性

红外深度传感器的探测面积见下图,

_images/tof.png

其发出的是一个角度为 20° 的圆锥光,这个光斑 D 与距离 Dist 的关系:

D=2×Dist×tan⁡(10)

要实现最佳测试效果,应保证目标物的尺寸要至少等于 TOF 光斑的尺寸。

小技巧

如果目标物小于光斑大小,那么应保证目标物尽量在光斑的中心位置,因为光斑内的光强分布并不是均匀的,而是呈一个类高斯分布,中间光强大,四周光强小,为了保证返回光能量足够,应尽量保证目标物在光斑中心。

引脚说明

_images/tof_module.png

这里介绍红外深度传感器的UART口:

编号 引脚 功能 对应连接项
1 VCC 供电 电源正极
2 GND 供电 电源地
3 TX 发送 RX
4 RX 接收 TX

通讯协议和数据格式

通讯接口 波特率 数据位 停止位 奇偶校验
UART 115200 8 1 none

控制命令输入:

ir_distance_sensor_measure_on
描述:打开红外深度传感器数据输出,输出频率为20hz
ir_distance_sensor_measure_off
描述:关闭红外深度传感器数据输出

数据输出:

ir distance:xxx
描述:红外深度传感器数据格式

小技巧

命令格式都以字符串形式输入和输出

Python API

请参考 红外深度传感器

传感器转接模块

介绍

传感器转接模块是为了方便用户将温度、压力、测距等传感器接入 RoboMaster EP而设计的,可在Scratch 编程环境中获取传感器数据信息,每个模块均有两个传感器接口,两个接口功能相同。

_images/pinboard.png

引脚说明

端口 引脚 功能
port1 VCC 电源正极,输出电压3.3V
GND 电源地
I/O 电平输入,输入范围0~3.3V
AD 模拟电压输入,输入范围0~3.3V
port2 同Port1 同port1

Python API

请参考 传感器转接模块

UART 接口

介绍

UART 是第三方平台跟 EP 连接的一种方式。用户通过 UART 可以很方便的将搭载在 EP 上的单片机跟 EP 建立连接,并在单片机上实现交互逻辑,使用明文 SDK 和 EP 机器人进行通信,实现对 EP 自动化的控制。

引脚说明

EP 的 UART 在运动控制器上,引脚说明如下:

_images/uart.png

串口配置

通讯接口 波特率 数据位 停止位 奇偶校验
UART 115200 8 1 none

第三方平台连接方式

请参考 UART 连接

Python 编程示例

  1. PC 通过串口转 USB 连接到 EP 运动控制器的 UART 上。

  2. PC 端开启串口调试助手,选择打开串口对应 COM 口。

  3. 打开已跟 EP 建立连接设备的官方 App,进入 Python 编程模式。

  4. 在 Python 编程界面下,写一个简单的程序,使用 read_string() 读取串口数据,打印出来后再通过 write_string() 进行转发,并点击 “开始” 按钮运行程序。

  5. 在串口调试助手上发送一个字符串,看是否能正确收到发出去的字符串。并查看 App 上是否正确打印了收到的字符串。

    _images/uart_serial.png

    串口调试助手发送并回显字符串

    _images/uart_pc.png

    App 打印收到的字符串并进行转发

明文 SDK 示例

  1. PC 通过串口转 USB 连接到 EP 运动控制器的 UART 上。

  2. PC 端开启串口调试助手,选择打开串口对应 COM 口。

  3. 在串口调试助手上发送字符串 command;,若能收到 EP 发回来的 ok 表示明文 SDK 解析成功。

    _images/uart_serial_sdk.png

    串口调试助手发送 SDK 字符串收到回应

警告

在通过 UART 发送明文 SDK 指令时,一定要记得在命令后面加 ; 分号,不然会解析失败。

Python API

请参考 UART

明文 SDK 介绍

RoboMaster EP 最重要的一个功能是支持明文 SDK,包含各个内置模块和拓展模块的控制接口,以及视频流、音频流的输出接口。 EP 支持 USB、 WIFI、 UART 等多种接入方式,用户可根据平台接口选择任意方式接入。

明文 SDK 极大的丰富了 EP 的扩展性,能方便的和 第三方平台通信,提供了二次开发的可能性。下面将使用 Wi-Fi 直接连接 方式(其他连接模式请参考 建立连接),以完成 控制发射器发射 功能为例,介绍SDK中明文协议的使用。

开发前的准备

  1. 准备一台 PC 电脑,需具备 Wi-Fi 功能。
  2. PC 上搭建 Python 3.x 环境,安装方式请参考 Python Getting Started

建立连接

  1. 开启电源

    开启机器人电源,切换智能中控的连接模式开关至 直连模式

    _images/direct_connection_change.png
  2. 建立Wi-Fi连接

    打开电脑的无线网络访问列表,选择位于机身贴纸上对应的 Wi-Fi 名称,输入 8 位密码,选择连接

  3. 准备连接脚本

    在完成 Wi-Fi 后,我们还需要编程与机器人建立 TPC/IP 连接,并在对应的端口上传输特定的 明文协议,就可以实现相应的控制,更多 明文协议 请参考 协议内容

    这里我们以 Python 编程语言为例,编写脚本来完成 建立控制连接,接收用户指令,传输明文协议 的过程,达到控制机器人的目的。

    参考代码如下

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
# -*- encoding: utf-8 -*-
# 测试环境: Python 3.6 版本

import socket
import sys

# 直连模式下,机器人默认 IP 地址为 192.168.2.1, 控制命令端口号为 40923
host = "192.168.2.1"
port = 40923

def main():

        address = (host, int(port))

        # 与机器人控制命令端口建立 TCP 连接
        s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

        print("Connecting...")

        s.connect(address)

        print("Connected!")

        while True:

                # 等待用户输入控制指令
                msg = input(">>> please input SDK cmd: ")

                # 当用户输入 Q 或 q 时,退出当前程序
                if msg.upper() == 'Q':
                        break

                # 添加结束符
                msg += ';'

                # 发送控制命令给机器人
                s.send(msg.encode('utf-8'))

                try:
                        # 等待机器人返回执行结果
                        buf = s.recv(1024)

                        print(buf.decode('utf-8'))
                except socket.error as e:
                        print("Error receiving :", e)
                        sys.exit(1)
                if not len(buf):
                        break

        # 关闭端口连接
        s.shutdown(socket.SHUT_WR)
        s.close()

if __name__ == '__main__':
        main()
  1. 将上述代码保存为 rm_sdk.py

  2. 运行脚本

    运行 rm_sdk.py 文件 (Windows系统在安装完成Python环境后可直接双击 *.py 文件运行,若无法运行,请按键 win+r 并输入 cmd,按回车后打开命令运行, 键入 python rm_sdk.py 运行;Linux系统请按键 ctrl+alt+t 打开命令行键入 python rm_sdk.py)

  3. 建立 TCP/IP 控制连接

    当运行窗口输出 Connecting... 时,代表正在尝试与机器人建立连接,当运行窗口输出 Connected! 时,表示已经成功建立控制连接。

使能 SDK 模式

要进行 SDK 控制,我们需要控制机器人进入 SDK 模式。 在上述 Python 运行窗口输入 command 命令,按回车键,程序将会发送该命令至机器人,返回 ok 即机器人成功进入 SDK 模式:

>>> please input SDK cmd: command
ok

成功进入 SDK 模式后,我们就可以输入控制命令来进行机器人的控制了。

发送控制命令

继续输入 blaster fire ,返回 ok ,同时,发射器会发射一次:

>>> please input SDK cmd: blaster fire
ok

此时,您可以输入其他控制指令来进行机器人控制,更多控制指令请参考 明文协议

退出 SDK 模式

在完成我们的所有控制指令之后,我们需要退出 SDK 模式,这样我们机器人的其他功能才可以正常使用。

输入 quit, 退出 SDK 模式,退出 SDK 模式后无法继续使用 SDK 功能,若要使用,请重新输入 command 进入 SDK 模式:

>>> please input SDK cmd: quit
ok

小结

上面我们通过与机器人建立物理连接,与机器人建立 TCP/IP 控制连接,控制机器人进入 SDK 模式,发送控制指令,退出 SDK 模式等几个步骤,实现了通过 SDK 对机器人进行相关的控制功能。您可以通过增加其中 发送控制指令 部分的内容,来实现更为复杂的逻辑,完成更为有趣的功能。

其中 Python 编程控制部分,如果您更熟悉其他语言的使用,也可以使用其他语言完成整个控制流程。

如果您手边的设备不支持 Wi-Fi 无法使用 Wi-Fi 直接连接,可以参考 连接 使用其他连接模式。

以上就是 SDK 快速入门内容,更多使用细节请参见 SDK文档,更多示例代码请参见 RoboMaster Sample Code

接入方式

连接方式

机器人支持多种连接方式,可通过任意一种连接方式接入使用 SDK 功能

  • 直接连接

    1. Wi-Fi 直连 :通过将机器人设置为直连模式,并连接机器人的 Wi-Fi 热点进行接入
    2. USB 连接 :通过机器人的智能中控上的 USB 端口接入(需支持 RNDIS 功能)
    3. UART 连接 :通过机器人的运动控制器上的 UART 接口接入
  • 组网连接

    1. Wi-Fi 组网 :通过将机器人设置为组网模式,并将计算设备与机器人加入到同一个局域网内,实现组网连接

连接参数

  1. Wi-Fi 直连/Wi-Fi 组网/USB 连接方式请参考以下参数配置:
  • IP 地址说明

    • Wi-Fi 直连模式下,机器人默认 IP 为 192.168.2.1
    • Wi-Fi 组网模式下,机器人 IP 由路由器动态分配,可通过监听 IP 广播 数据端口来获取当前局域网内机器人 IP 地址来进行连接
    • USB 连接模式下,需要计算设备支持 RNDIS 功能,机器人默认 IP 为 192.168.42.2
  • 端口及连接方式说明

数据 端口号 连接方式 说明
视频流 40921 TCP 需执行开启视频流推送命令,才有数据输出
音频流 40922 TCP 需执行开启音频流推送命令,才有数据输出
控制命令 40923 TCP 可通过当前通道使能 SDK 模式,参见 SDK 模式控制
消息推送 40924 UDP 需执行开启消息推送命令,才有数据输出
事件上报 40925 TCP 需执行开启事件上报命令,才有数据输出
IP 广播 40926 UDP 当机器人未与任何设备建立连接时,会有数据输出
  1. UART 连接方式请参考以下 UART 参数配置
波特率 数据位 停止位 校验位
115200 8 1 None

警告

UART 连接方式下的数据说明:

UART 连接方式下,仅提供 控制命令/消息推送/事件上报 数据,如需 视频流/音频流 数据,请使用 Wi-Fi/USB 连接模式

连接示例

下面我们将以 Python 编程语言为基础,介绍多种连接方式的使用范例。以下所有示例中,默认 PC 上需要集成 Python 3.x 环境(安装方式请参考 Python Getting Started),后面不再赘述。

WIFI 直连模式

  • 环境准备
  1. 准备一台 PC 电脑,需具备 Wi-Fi 功能。
  • 建立连接
  1. 开启电源

    开启机器人电源,切换智能中控的连接模式开关至 直连模式

    _images/direct_connection_change.png
  2. 建立 Wi-Fi 连接

    打开电脑的无线网络访问列表,选择位于机身贴纸上对应的 Wi-Fi 名称,输入 8 位密码,选择连接

  3. 准备连接脚本

    建立 Wi-Fi 连接后,我们还需要编程与机器人建立 TPC/IP 连接 机器人开放多个连接端口可供连接,我们首先应完成 控制命令端口 的连接(直连模式下机器人 IP 地址为 192.168.2.1, 控制命令端口号: 40923),以使能机器人 SDK 模式。

    这里我们以 Python 编程语言为例,编写脚本来完成 建立控制连接,使能 SDK 模式 功能

    参考代码如下

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    # -*- encoding: utf-8 -*-
    # 测试环境: Python 3.6 版本
    
    import socket
    import sys
    
    # 直连模式下,机器人默认 IP 地址为 192.168.2.1, 控制命令端口号为 40923
    host = "192.168.2.1"
    port = 40923
    
    def main():
    
            address = (host, int(port))
    
            # 与机器人控制命令端口建立 TCP 连接
            s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
            print("Connecting...")
    
            s.connect(address)
    
            print("Connected!")
    
            while True:
    
                    # 等待用户输入控制指令
                    msg = input(">>> please input SDK cmd: ")
    
                    # 当用户输入 Q 或 q 时,退出当前程序
                    if msg.upper() == 'Q':
                            break
    
                    # 添加结束符
                    msg += ';'
    
                    # 发送控制命令给机器人
                    s.send(msg.encode('utf-8'))
    
                    try:
                            # 等待机器人返回执行结果
                            buf = s.recv(1024)
    
                            print(buf.decode('utf-8'))
                    except socket.error as e:
                            print("Error receiving :", e)
                            sys.exit(1)
                    if not len(buf):
                            break
    
            # 关闭端口连接
            s.shutdown(socket.SHUT_WR)
            s.close()
    
    if __name__ == '__main__':
            main()
    
  4. 将上述代码保存为 rm_direct_connection_sdk.py

  5. 运行脚本

    Windows 系统 在安装完成 Python 环境后可直接双击*.py 文件运行,若无法运行,请按 win+r 并输入 cmd,按回车后打开命令运行, 键入 python rm_direct_connection_sdk.py 运行;

    Linux 系统 请按 ctrl+alt+t 打开命令行键入 python rm_direct_connection_sdk.py 运行

  6. 建立 TCP/IP 控制连接

    当运行窗口输出 Connecting... 时,代表正在尝试与机器人建立连接,当运行窗口输出 Connected! 时,表示已经成功建立控制连接。

  • 验证

在成功建立控制连接后,在命令行里输入 command, 机器人返回 ok,则表示已经完成连接,并且机器人进入 SDK 模式成功,之后你就可以输入任意控制指令进行机器人控制了。

  • 其他

UART物理链路连接示例请参考:UART

WIFI 路由器模式

  • 环境准备
  1. 准备一台 PC 电脑,具备网络功能(Wi-Fi 或者有线网络皆可)
  2. 准备一台家用路由器
  • 建立连接
  1. 开启电源

    开启机器人电源,切换智能中控的连接模式开关至 组网模式

    _images/networking_connection_change.png
  2. 建立组网连接

    Wi-Fi:

    若使用 Wi-Fi 连接,请将 PC 电脑通过 Wi-Fi 连接至路由器上

    有线网络:

    若使用有线网络连接,请将 PC 电脑通过网线连接至路由器的 LAN 口

    确保 PC 已经接入路由器后,打开 RoboMaster 程序,进入组网连接页面,按下机器人智能中控上的扫码连接按键,扫描二维码进行组网连接,直到连接成功。

    _images/networking_connection_key.png
  3. 获取机器人在局域网内的 IP 地址

    在完成组网连接后,我们的 PC 机已经和机器人处于同一个局域网内,接下来需要编程与机器人建立 TPC/IP 连接,并连接到 控制命令端口 端口,以使能机器人 SDK 模式。

    若您使用的路由器开启了 DHCP 服务,则机器人的 IP 地址为路由器动态分配,我们需要进一步获取机器人在局域网内的 IP 地址。这里提供两种办法获取:

    1. 若您通过 RoboMaster 程序进行的组网连接,则进入 RoboMaster 程序的 设置->连接 页面,机器人在局域网内的 IP 地址会在此处显示。
    2. 若您通过其他方式进行的组网连接,则需要通过 监听机器人地址广播 来获取机器人在局域网内的 IP 地址,更多细节请参考 广播 部分。

    参考代码如下

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    # -*- encoding: utf-8 -*-
    import socket
    
    ip_sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    
    # 绑定 IP 广播端口
    ip_sock.bind(('0.0.0.0', 40926))
    
    # 等待接收数据
    ip_str = ip_sock.recvfrom(1024)
    
    # 输出数据
    print(ip_str)
    

    将上述代码保存为 rm_get_robot_ip.py, 运行上述代码,命令行输出:

    robot ip 192.168.0.115
    

    我们可以看到,通过 监听机器人地址广播 可以获取到机器人在局域网内的 IP 地址为 192.168.0.115

  1. 准备连接脚本

    我们已经获取到机器人的 IP 地址,这里我们仍以 Python 编程语言为例,编写脚本来完成 建立控制连接,使能 SDK 模式 功能

    参考代码如下

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    # -*- encoding: utf-8 -*-
    # 测试环境:Python 3.6 版本
    
    import socket
    import sys
    
    # 组网模式下,机器人当前 IP 地址为 192.168.0.115, 控制命令端口号为 40923
    # 机器人 IP 地址根据实际 IP 进行修改
    host = "192.168.0.115"
    port = 40923
    
    def main():
    
            address = (host, int(port))
    
            # 与机器人控制命令端口建立 TCP 连接
            s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
            print("Connecting...")
    
            s.connect(address)
    
            print("Connected!")
    
            while True:
    
                    # 等待用户输入控制指令
                    msg = input(">>> please input SDK cmd: ")
    
                    # 当用户输入 Q 或 q 时,退出当前程序
                    if msg.upper() == 'Q':
                            break
    
                    # 添加结束符
                    msg += ';'
    
                    # 发送控制命令给机器人
                    s.send(msg.encode('utf-8'))
    
                    try:
                            # 等待机器人返回执行结果
                            buf = s.recv(1024)
    
                            print(buf.decode('utf-8'))
                    except socket.error as e:
                            print("Error receiving :", e)
                            sys.exit(1)
                    if not len(buf):
                            break
    
            # 关闭端口连接
            s.shutdown(socket.SHUT_WR)
            s.close()
    
    if __name__ == '__main__':
            main()
    
  2. 将上述代码保存为 rm_networking_connection_sdk.py

  3. 运行脚本

    Windows 系统:在安装完成 Python 环境后可直接双击*.py 文件运行,若无法运行,请按 win+r 并输入 cmd,按回车后打开命令运行, 键入 python rm_networking_connection_sdk.py 运行;

    Linux 系统 请按:ctrl+alt+t 打开命令行键入 python rm_networking_connection_sdk.py 运行

  4. 建立 TCP/IP 控制连接

    当运行窗口输出 Connecting... 时,代表正在尝试与机器人建立连接,当运行窗口输出 Connected! 时,表示已经成功建立控制连接。

  • 验证

在成功建立控制连接后,在命令行里输入 command, 机器人返回 ok,则表示已经完成连接,并且机器人进入 SDK 模式成功,之后你就可以输入任意控制指令进行机器人控制了。

USB 连接

USB 连接模式,实质上是使用 RNDIS 协议,将机器人上的 USB 设备虚拟为一张网卡设备,通过 USB 发起 TCP/IP 连接。更多 RNDIS 内容请参见 RNDIS Wikipedia

  • 环境准备
  1. 准备一台具备 RNDIS 功能的 PC 电脑(请确认 PC 电脑上已经配置好 RNDIS 功能)
  2. 准备一根 Micro-USB 数据线
  • 建立连接
  1. 开启电源

    开启机器人电源,无需关心连接模式开关位置

  2. 建立 USB 连接

    将 USB 数据线接入到机器人智能中控上的 USB 口,另一端与电脑相连

  3. 测试连接

    打开命令行窗口,运行:

    ping 192.168.42.2
    

    若命令行输出通信成功,则表示链路正常,可以进行下一步,如:

    PING 192.168.42.2 (192.168.42.2) 56(84) bytes of data.
    64 bytes from 192.168.42.2: icmp_seq=1 ttl=64 time=0.618 ms
    64 bytes from 192.168.42.2: icmp_seq=2 ttl=64 time=1.21 ms
    64 bytes from 192.168.42.2: icmp_seq=3 ttl=64 time=1.09 ms
    64 bytes from 192.168.42.2: icmp_seq=4 ttl=64 time=0.348 ms
    64 bytes from 192.168.42.2: icmp_seq=5 ttl=64 time=0.342 ms
    
    --- 192.168.42.2 ping statistics ---
    5 packets transmitted, 5 received, 0% packet loss, time 4037ms
    rtt min/avg/max/mdev = 0.342/0.723/1.216/0.368 ms
    

    若命令行输出 无法访问… 或者显示超时,则需要检查 PC 上 RNDIS 服务是否配置正常,并重启小车重试,如:

    PING 192.168.42.2 (192.168.42.2) 56(84) bytes of data.
    
    --- 192.168.42.2 ping statistics ---
    

4 packets transmitted, 0 received, 100% packet loss, time 3071ms

  1. 准备连接

    连接过程与 WIFI 直连模式 -> 准备连接脚本 类似,需要将机器人 IP 地址替换为 USB 模式下的 IP 地址,其余代码与步骤保持不变即可,这里不再赘述

    参考代码变更如下

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    # -*- encoding: utf-8 -*-
    # 测试环境: Python 3.6 版本
    
    import socket
    import sys
    
    # USB 模式下,机器人默认 IP 地址为 192.168.42.2, 控制命令端口号为 40923
    host = "192.168.42.2"
    port = 40923
    
    # other code
    
  • 验证

在成功建立控制连接后,在命令行里输入 command, 机器人返回 ok,则表示已经完成连接,并且机器人进入 SDK 模式成功,之后你就可以输入任意控制指令进行机器人控制了。

UART 连接

  • 环境准备
  1. 一台 PC 电脑,并确定已安装 USB 转串口模块驱动
  2. USB 转串口模块
  3. 三根杜邦线
  • 建立连接
  1. 开启电源

    开启机器人电源,无需关心连接模式开关位置

  2. 连接 UART

    将杜邦线插在机器人底盘主控上的 UART 接口上,分别插在 GND, RX, TX 引脚上,另一端对应插在 USB 转串口模块的 GND, TX, RX 引脚

  3. 配置 UART,建立通信连接

    这里,我们仍以 Python 编程为例,进行 Windows 系统下 UART 相关配置。

    1. 确认 PC 已识别 USB 转串口模块,并在 电脑设备管理器 中的 端口 里确认对应的串口号,如 COM3。

    2. 安装 serial 模块:

      pip install pyserial
      
    3. 编写代码进行 UART 控制,参考代码如下

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    # -*- encoding: utf-8 -*-
    # 测试环境:Python 3.6 版本
    import serial
    
    ser = serial.Serial()
    
    # 配置串口 波特率 115200,数据位 8 位,1 个停止位,无校验位,超时时间 0.2 秒
    ser.port = 'COM3'
    ser.baudrate = 115200
    ser.bytesize = serial.EIGHTBITS
    ser.stopbits = serial.STOPBITS_ONE
    ser.parity = serial.PARITY_NONE
    ser.timeout = 0.2
    
    # 打开串口
    ser.open()
    
    while True:
    
            # 等待用户输入控制指令
            msg = input(">>> please input SDK cmd: ")
    
            # 当用户输入 Q 或 q 时,退出当前程序
            if msg.upper() == 'Q':
                    break
    
            # 添加结束符
            msg += ';'
    
            ser.write(msg.encode('utf-8'))
    
            recv = ser.readall()
    
            print(recv.decode('utf-8'))
    
    # 关闭串口
    ser.close()
    
    1. 将上述程序保存为 rm_uart.py, 并运行
  • 验证

在成功建立控制连接后,在命令行里输入 command;, 机器人返回 ok,则表示已经完成连接,并且机器人进入 SDK 模式成功,之后你就可以输入任意控制指令进行机器人控制了。

小技巧

示例代码

更多连接相关示例代码请参考 RoboMaster Sample Code

明文协议

协议格式

控制命令

IN:<obj> <command> <params> [<seq>];

  • 描述
    • 控制命令协议格式,一般用来与机器人做控制上的交互
    • 作为结束符
  • 参数
    • obj (str): 控制对象字符串
    • command (str): 控制命令字符串
    • params (str): 命令参数字符串,一般为 <key> <value> 形式
    • seq (str): 命令序号字符串,一般为 seq <seq_value> 形式,可选参数

OUT:<result> [<seq>]

  • 描述
    • 控制命令响应结果协议格式,一般用来确认控制命令执行结果
    • 不做特殊说明的情况下,所有控制命令均有响应结果
  • 参数
    • result (exec_result_enum): 执行结果字符串
    • seq (str): 执行结果序号字符串,一般为 seq <seq_value> 形式

注解

<seq>

<seq> 可用来标识当前消息的唯一性,当控制命令中带有 <seq> 参数时, 对应命令的响应结果结果中即包含对应的序号

消息推送

OUT: <obj> push <attr> <value>

  • 描述
    • 消息推送协议格式,通过控制命令打开某消息推送后即可接收到
    • 消息推送将会以固定的频率进行的推送,推送频率取决于使能当前消息推送时的频率设置
  • 参数
    • obj (str): 推送对象
    • attr (str): 推送数据属性
    • value (str): 推送数据数值

事件上报

OUT: <obj> event <attr> <value>

  • 描述
    • 事件上报协议格式,通过控制命令打开某事件上报开关后即可接收到
  • 参数
    • obj (str): 发生事件的对象
    • attr (str): 事件数据属性
    • value (str) 事件数据数值

注解

触发机制

当成功使能对应 事件上报 功能后,若发生事件,则会进行一次事件上报

IP 广播

OUT: robot ip <addr>

  • 参数
    • addr (str): 当前连接模式下的机器人的 IPv4 地址

注解

广播生命周期

当处于 Wi-Fi 组网 模式下,机器人会不断在对应端口上广播自己的 IPv4 地址,您可通过该 IP 地址连接到机器人,当成功连接后,广播停止

视频流

OUT: H.264编码实时视频流数据 (1280*720 @ 30FPS),需要对视频流数据进行正确的解码操作才能实时显示视频画面。

音频流

OUT: Opus 编码实时音频流数据,需要对音频流数据进行正确的解码操作才能实时播放音频。

小技巧

Decoder

接收端音视频解码示例代码请参见 Stream Decoder

注解

IN/OUT

该文档中,控制指令中出现的前缀 IN 或者 OUT 在控制指令中无实际意义,仅为标识以机器人为主体的情况下,当前指令的数据流向:

IN:标识当前数据为从外部设备发送至机器人

OUT:标识当前数据为从机器人发送至外部设备

实际使用中,请忽略该标识,仅发送和接收实际的控制命令即可

协议内容

SDK 模式控制

进入 SDK 模式

IN:command

  • 描述
    • 控制机器人进入 SDK 模式
    • 当机器人成功进入 SDK 模式后,才可以响应其余控制命令
退出 SDK 模式

IN: quit

  • 描述
    • 控制机器人退出 SDK 模式,重置所有设置项
    • Wi-Fi/USB 连接模式下,当连接断开时,机器人会自动退出 SDK 模式

机器人控制

机器人运动模式控制

IN:robot mode <mode>

  • 描述
    • 设置机器人运动模式
  • 参数
  • 示例
    • robot mode chassis_lead; : 将机器人的运动模式设置为“云台跟随底盘模式”

注解

机器人运动模式

机器人运动模式描述了云台与底盘之前相互作用与相互运动的关系,每种机器人模式都对应了特定的作用关系。

机器人运动模式分为三种模式:

  1. 云台跟随底盘模式:该模式下,云台的 YAW 轴会进入持续跟随底盘 YAW 轴的运动的状态,云台将不响应所有控制指令中 YAW 轴控制的部分,影响指令有 云台运动速度控制 云台相对位置控制 云台绝对位置控制
  2. 底盘跟随云台模式:该模式下,底盘的 YAW 轴会进入持续跟随云台 YAW 轴的运动的状态,底盘将不响应所有控制指令中 YAW 轴控制的部分,影响指令有 底盘运动速度控制 底盘轮子速度控制 底盘相对位置控制
  3. 自由模式:该模式下,云台的 YAW 轴与底盘的 YAW 轴运动互不影响
机器人运动模式获取

IN: robot mode ?

  • 描述
    • 查询当前机器人运动模式
  • 返回值
  • 示例
    • IN:robot mode ?; : 查询当前的机器人运动模式
    • OUT: chassis_lead : 机器人返回当前的运动模式为 云台跟随底盘模式

警告

获取指令中的 ?

注意:查询指令中的 ? 与前面命令部分中间存在一个空格

机器人剩余电量获取

IN: robot battery ?

  • 描述
    • 查询当前机器人剩余电量
  • 返回值
    • battery_percentage (int:[1-100]): 机器人剩余电量,满电量为100
  • 示例
    • IN:robot battery ?; : 查询当前的机器人剩余电量
    • OUT: 20 : 机器人返回当前的剩余电量为 20

底盘控制

底盘运动速度控制

IN: chassis speed x <speed_x> y <speed_y> z <speed_z>

  • 描述
    • 控制底盘运动速度
  • 参数
    • speed_x (float:[-3.5,3.5]): x 轴向运动速度,单位 m/s
    • speed_y (float:[-3.5,3.5]): y 轴向运动速度,单位 m/s
    • speed_z (float:[-600,600]): z 轴向旋转速度,单位 °/s
  • 示例
    • chassis speed x 0.1 y 0.1 z 1; : 底盘 x 轴速度为 0.1 m/s,y 轴速度为 0.1 m/s,z 轴旋转速度为 1°/s
底盘轮子速度控制

IN: chassis wheel w1 <speed_w1> w2 <speed_w2> w3 <speed_w3> w4 <speed_w4>

  • 描述
    • 控制四个轮子的速度
  • 参数
    • speed_w1 (int:[-1000, 1000]): 右前麦轮速度,单位 rpm
    • speed_w2 (int:[-1000, 1000]): 左前麦轮速度,单位 rpm
    • speed_w3 (int:[-1000, 1000]): 右后麦轮速度,单位 rpm
    • speed_w4 (int:[-1000, 1000]): 左后麦轮速度,单位 rpm
  • 示例
    • chassis wheel w2 100 w1 12 w3 20 w4 11; : 底盘左前麦轮的速度为 100 rpm,右前麦轮速度为 12 rpm,右后麦轮速度为 20 rpm,左后麦轮速度为 11 rpm
底盘相对位置控制

IN: chassis move { [x <distance_x>] | [y <distance_y>] | [z <degree_z>] } [vxy <speed_xy>] [vz <speed_z>]

  • 描述
    • 控制底盘运动当指定位置,坐标轴原点为当前位置
  • 参数
    • distance_x (float:[-5, 5]): x 轴向运动距离,单位 m
    • distance_y (float:[-5, 5]): y 轴向运动距离,单位 m
    • degree_z (int:[-1800, 1800]): z 轴向旋转角度,单位 °
    • speed_xy (float:(0, 3.5]): xy 轴向运动速度,单位 m/s
    • speed_z (float:(0, 600]): z 轴向旋转速度, 单位 °/s
  • 示例
    • chassis move x 0.1 y 0.2; :以当前位置为坐标原点,向 x 轴运动 0.1 m,向 y 轴运动 0.2 m
底盘速度获取

IN: chassis speed ?

  • 描述
    • 获取底盘速度信息
  • 返回值
    • <x> <y> <z> <w1> <w2> <w3> <w4> :x 轴向运动速度(m/s),y 轴向运动速度(m/s),z 轴向旋转速度(°/s),w1 右前麦轮速度(rpm),w2 左前麦轮速速(rpm),w3 右后麦轮速度(rpm),w4 左后麦轮速度(rpm)
  • 示例
    • IN: chassis speed ?; : 获取底盘的运动速度信息
    • OUT: 1 2 30 100 150 200 250; : 底盘当前的 x 轴向运动速度为 1 m/s,y 轴向运动速度 2 m/s,z 轴向旋转速度为 20°/s,1 号轮子转速为 100 rpm,2 号轮子转速为 100 rpm,3 号轮子转速为 100 rpm,4 号轮子转速为 100 rpm
底盘位置获取

IN: chassis position ?

  • 描述
    • 获取底盘位置信息
  • 返回值
    • <x> <y> <z> :x 轴位置(m),y 轴位置(m),偏航角度(°)
  • 示例
    • IN: chassis position ?; :获取底盘的位置信息
    • OUT: 1 1.5 20 :底盘当前的位置距离上电时刻位置,沿 x 轴运动了 1 m,沿 y 轴运动了 1.5 m,旋转了 20°
底盘姿态获取

IN: chassis attitude ?

  • 描述
    • 获取底盘姿态信息
  • 返回值
    • <pitch> <roll> <yaw> :pitch 轴角度(°),roll 轴角度(°),yaw 轴角度(°)
  • 示例
    • chassis attitude ?; :查询底盘的姿态信息
底盘状态获取

IN: chassis status ?

  • 描述
    • 获取底盘状态信息
  • 返回值
    • <static> <uphill> <downhill> <on_slope> <pick_up> <slip> <impact_x> <impact_y> <impact_z> <roll_over> <hill_static>
      • static:是否静止
      • uphill:是否上坡
      • downhill:是否下坡
      • on_slope:是否溜坡
      • pick_up:是否被拿起
      • slip:是否滑行
      • impact_x:x 轴是否感应到撞击
      • impact_y:y 轴是否感应到撞击
      • impact_z:z 轴是否感应到撞击
      • roll_over:是否翻车
      • hill_static:是否在坡上静止
  • 示例
    • IN: chassis status ?; :查询底盘的状态
    • OUT: 0 1 0 0 0 0 0 0 0 0 0 : 底盘当前处于上坡状态
底盘信息推送控制

IN:chassis push {[position <switch> pfreq <freq>][attitude <switch> afreq <freq>] | [status <switch> sfreq <switch>] [freq <freq_all>]}

  • 描述
    • 打开/关闭底盘中相应属性的信息推送
    • 频率设置
      • 各单独的功能支持单独的频率设置,如:
        • chassis push position on pfreq 1 attitude on : 打开位置和姿势推送,位置推送频率为 1 Hz,姿势推送频率使用默认设置 5 Hz
      • 支持当前模块所有功能频率统一设置,如:
        • chassis push freq 10 #chassis 推送统一为 10 Hz
        • chassis push position pfreq 1 freq 5 #此时有 freq 参数,将会忽略 pfreq
      • 支持的频率 1, 5, 10, 20, 30, 50
    • 推送数据格式参见 底盘推送信息数据
  • 参数
    • switch (switch_enum) :当此处参数使用 on 时,表示打开对应属性的推送;当此处参数使用 off 时,表示关闭对应属性的推送
    • freq (int:(1,5,10,20,30,50)) :对应的属性推送的推送频率
    • freq_all (int:(1,5,10,20,30,50)) : 整个底盘所有相关推送信息的推送频率
  • 示例
    • chassis push attitude on; : 打开底盘姿态信息推送
    • chassis push attitude on status on; :打开底盘姿态、状态信息推送
    • chassis push attitude on afreq 1 status on sfreq 5; :打开底盘的姿态信息推送,推送频率为每秒一次,同时打开底盘的状态信息推送,推送频率为每秒五次
    • chassis push freq 10; :底盘所有信息推送的频率为每秒十次
底盘推送信息数据

OUT: chassis push <attr> <data>

  • 描述
    • 当用户使能底盘信息推送后,机器人会以设置的频率向用户推送相应信息
  • 参数
    • attr (chassis_push_attr_enum) : 订阅的属性名称
    • data : 订阅的属性数据
      • attrposition 时,data 内容为 <x> <y>
      • attrattitude 时,data 内容为 <pitch> <roll> <yaw>
      • attrstatus 时,data 内容为 <static> <uphill> <downhill> <on_slope> <pick_up> <slip> <impact_x> <impact_y> <impact_z> <roll_over> <hill_static>
  • 示例
    • chassis push attitude 0.1 1 3; :当前底盘的 pitch、roll、yaw 姿态信息分别为 0.1、1、3

云台控制

云台运动速度控制

IN: gimbal speed p <speed> y <speed>

  • 描述
    • 控制云台运动速度
  • 参数
    • p (float:[-450, 450]) :pitch 轴速度,单位 °/s
    • y (float:[-450, 450]) :yaw 轴速度,单位 °/s
  • 示例
    • gimbal speed p 1 y 1; :云台的 pitch 轴速度为 1°/s,yaw 轴速度为 1°/s
云台相对位置控制

IN: gimbal move { [p <degree>] [y <degree>] } [vp <speed>] [vy <speed>]

  • 描述
    • 控制云台运动到指定位置,坐标轴原点为当前位置
  • 参数
    • p (float:[-55, 55]) :pitch 轴角度, 单位 °
    • y (float:[-55, 55]) :yaw 轴角度,单位 °
    • vp (float:[0, 540]) :pitch 轴运动速速,单位 °/s
    • vy (float:[0, 540]) :yaw 轴运动速度,单位 °/s
  • 示例
    • gimbal move p 10; :以当前位置为坐标基准,控制云台运动到 pitch 轴角度为 10° 的状态
云台绝对位置控制

IN: gimbal moveto { [p <degree>] [y <degree>] } [vp <speed>] [vy <speed>]

  • 描述
    • 控制云台运动到指定位置,坐标轴原点为上电位置
  • 参数
    • p (int:[-25, 30]) :pitch 轴角度(°)
    • y (int:[-250, 250]) :yaw 轴角度(°)
    • vp (int:[0, 540]) :pitch 轴运动速度(°)
    • vy (int:[0, 540]) :yaw 轴运动速度(°)
  • 示例
    • gimbal moveto p 10 y -20 vp 0.1; :以机器人上电位置为坐标基准,控制云台运动到 pitch 轴角度为 10°,yaw 轴角度为 -20° 的状态,运动时指定 pitch 轴的运动速度为 0.1°/s
云台休眠控制

IN: gimbal suspend

  • 描述
    • 控制云台进入休眠状态
  • 示例
    • gimbal suspend; :使云台进入休眠状态
云台恢复控制

IN: gimbal resume

  • 描述
    • 控制云台从休眠状态中恢复
  • 参数
    • None
  • 示例
    • gimbal resume; :使云台退出休眠状态

警告

休眠状态 当云台进入休眠状态时,云台两轴电机将会释放控制力,云台整体不响应任何控制指令。

要解除云台休眠状态,请参见 云台恢复控制

云台回中控制

IN: gimbal recenter

  • 描述
    • 云台回中
  • 示例
    • gimbal recenter; :控制云台回中
云台姿态获取

IN: gimbal attitude ?

  • 描述
    • 获取云台姿态信息
  • 返回值
    • <pitch> <yaw> :pitch 轴角度(°),yaw 轴角度(°)
  • 示例
    • IN:gimbal attitude ?; :查询云台的角度信息
    • OUT: -10 20 :云台当前 pitch 轴角度 -10°,yaw 轴角度 20°
云台信息推送控制

IN: gimbal push <attr> <switch> [afreq <freq_all>]

  • 描述
  • 参数
    • attr (gimbal_push_attr_enum) : 订阅的属性名称
    • switch (switch_enum) :当此处参数使用 on 时,表示打开对应属性的推送;当此处参数使用 off 时,表示关闭对应属性的推送
    • freq_all : 云台所有相关推送信息的推送频率
  • 示例
    • gimbal push attitude on; :打开云台的信息推送
云台推送信息数据

OUT: gimabal push <attr> <data>

  • 描述
    • 当用户使能云台信息推送后,机器人会以设置的频率向用户推送相应信息
  • 参数
    • attr (gimbal_push_attr_enum) : 订阅的属性名称
    • data: 订阅的属性数据
      • attrattitude 时,data 内容为 <pitch> <yaw>
  • 示例
    • gimbal push attitude 20 10; :当前云台的 pitch 角度为 20°,yaw 角度为 10°

发射器控制

发射器单次发射量控制

IN:blaster bead <num>

  • 描述
    • 设置发射器单次发射量
  • 参数
    • num (int:[1,5]) :发射量
  • 示例
    • blaster bead 2; :控制发射器单次发射两发
发射器发射控制

IN: blaster fire

  • 描述
    • 控制水弹枪发射一次
  • 示例
    • blaster fire; :控制水弹枪发射一次
发射器单次发射量获取

IN: blaster bead ?

  • 描述
    • 获取水弹枪单次发射的水弹数
  • 返回值
    • <num> :水弹枪单次发射的水弹数
  • 示例
    • IN: blaster bead ?; :查询水弹枪单次发射的水弹数
    • OUT: 3 :当前水弹枪单次发射水弹数量为 3

装甲板控制

装甲板灵敏度控制

IN: armor sensitivity <value>

  • 描述
    • 设置装甲板打击检测灵敏度
  • 参数
    • value (int:[1,10]) :装甲板灵敏度,数值越大,越容易检测到打击。默认灵敏度值为 5
  • 示例
    • armor sensitivity 1; :设置装甲板打击检测灵敏度为 1
装甲板灵敏度获取

IN: armor sensitivity ?

  • 描述
    • 获取装甲板打击检测灵敏度
  • 参数
    • <value> :装甲板灵敏度
  • 示例
    • IN: armor sensitivity ?; :查询装甲板打击检测灵敏度
    • OUT: 5 :查询装甲板打击检测灵敏度
装甲板事件上报控制

IN: armor event <attr> <switch>

装甲板事件上报数据

OUT: armor event hit <index> <type>

  • 描述
    • 当发生装甲板敲击事件时,可以从事件推送端口接收到此消息
  • 参数
    • index (int:[1, 6]) :当前发生敲击事件的装甲板 ID
      • 1 底盘后
      • 2 底盘前
      • 3 底盘左
      • 4 底盘右
      • 5 云台左
      • 6 云台右
    • type (int:[0, 2]) :当前敲击事件的种类
      • 0 水弹攻击
      • 1 撞击
      • 2 手敲击
  • 示例
    • armor event hit 1 0; :1 号装甲板检测到水弹枪攻击

声音识别控制

声音识别事件上报控制

IN: sound event <attr> <switch>

  • 描述
  • 参数
  • 示例
    • sound event applause on; :打开声音(掌声)识别
声音识别事件上报数据

OUT: sound event <attr> <data>

  • 描述
  • 参数
    • attr (sound_event_attr_enum): 事件属性名称
    • data :事件属性数据
      • attrapplause 时, data<count>,表示短时间内击掌的次数
  • 示例
    • sound event applause 2; :识别到短时间内有 2 次拍掌

PWM 控制

PWM 输出占空比控制

IN: pwm value <port_mask> <value>

  • 描述
    • PWM 输出占空比设置
  • 参数
    • port_mask (hex:0-0xffff) :PWM 拓展口掩码组合, 编号为 X 的输出口对应掩码为 1 << (X-1)
    • value (float:0-100) :PWM 输出占空比,默认输出为 12.5
  • 示例
    • pwm value 1 50; : 控制 1 号 PWM 口的占空比为 50%
PWM 输出频率控制

IN: pwm freq <port_mask> <value>

  • 描述
    • PWM 输出频率设置
  • 参数
    • port_mask (hex:0-0xffff) :PWM 拓展口掩码组合, 编号为 X 的输出口对应掩码为 1 << (X-1)
    • value (int:XXX) :PWM 输出频率值
  • 示例
    • pwm freq 1 1000; : 控制 1 号 PWM 口的频率为 1000 Hz

LED 控制

LED 灯效控制

IN:led control comp <comp_str> r <r_value> g <g_value> b <value> effect <effect_str>

  • 描述
    • 机器人 LED 灯效控制接口,可设置多种效果
    • 跑马灯效果仅可作用于云台两侧 LED
  • 参数
    • comp_str (led_comp_enum) :LED 编号
    • r_value (int:[0, 255]) :RGB 红色分量值
    • g_value (int:[0, 255]) :RGB 绿色分量值
    • b_value (int:[0, 255]) :RGB 蓝色分量值
    • effect_str (led_effect_enum) :LED 灯效类型
  • 示例
    • led control comp all r 255 g 0 b 0 effect solid; : 机器人所有 LED 常亮为红色

传感器转接板控制

传感器转接板 ADC 值获取

IN: sensor_adapter adc id <adapter_id> port <port_num> ?

  • 描述
    • 获取传感器转接板的 ADC 数值
  • 参数
    • adapter_id (int:[1, 6]) :转接板的 ID 号
    • port_num (int:[1, 2]) :port 的编号
  • 返回值
    • adc_value :测量得到相应转接板上指定端口的电压值,电压取值范围[0V, 3,3V]
  • 示例
    • IN: sensor_adapter adc id 1 port 1 ?; : 查询 1 号转接板上 1 号端口的 ADC 数值
    • OUT: 1.1 :当前查询端口 ADC 值为 1.1
传感器转接板 IO 值获取

IN: sensor_adapter io_level id <adapter_id> port <port_num> ?

  • 描述
    • 获取传感器转接板 IO 口的逻辑电平
  • 参数
    • adapter_id (int:[1, 6]) :转接板的 ID 号
    • port_num (int:[1, 2]) :port 的编号
  • 返回值
    • io_level_value :测量得到相应转接板上指定端口的逻辑电平值,0 或 1
  • 示例
    • IN: sensor_adapter io_level id 1 port 1 ?; :查询 1 号转接板上 1 号端口的 IO 逻辑电平
    • OUT: 1 :当前查询端口的 IO 值为 1
传感器转接板 IO 引脚电平跳变时间值获取

IN: sensor_adapter pulse_period id <adapter_id> port <port_num>

  • 描述
    • 获取传感器转接板 IO 口电平跳变持续时间
  • 参数
    • adapter_id (int:[1, 6]):转接板的 ID 号
    • port_num (int:[1, 2]):port 的编号
  • 返回值
    • pulse_period_value: 测量得到相应转接板上指定端口的电平跳变持续时间值,单位 ms
  • 示例
    • sensor_adapter pulse_period id 1 port 1; :查询 1 号转接板上 1 号端口的电平跳变持续时间
传感器转接板事件上报控制

IN: sensor_adapter event io_level <switch>

  • 描述
    • 打开/关闭传感器转接板电平跳变事件推送,打开后当 IO 上电平跳变时推送消息,见下一章中[传感器转接板电平跳变事件推送](#传感器转接板电平跳变推送)的介绍
  • 参数
    • switch (switch_enum):电平跳变事件上报的控制开关
  • 示例
    • sensor_adapter event io_level on; :打开传感器转接板的电平跳变事件推送、
传感器转接板事件上报数据

OUT: sensor_adapter event io_level (<id>, <port_num>, <io_level>)

  • 描述
    • 当传感器转接板发生电平跳变时推送,可以从事件推送端口接收到此消息
    • 需要打开传感器转接板电平跳变推送,参见 传感器转接板事件上报数据
  • 参数
    • id:传感器转接板的 ID
    • port_num:IO 的 ID
    • io_level:当前的逻辑电平值
  • 示例
    • sensor_adapter event io_level (1, 1, 0); :当前 1 号转接板的 1 号 IO 的逻辑电平跳变为 0

红外深度传感器控制

红外深度传感器开关控制

IN: ir_distance_sensor measure <switch>

  • 描述
    • 打开/关闭所有红外传感器开关
  • 参数
  • 示例
    • ir_distance_sensor measure on; :打开所有红外深度传感器
红外深度传感器距离获取

IN: ir_distance_sensor distance <id> ?

  • 描述
    • 获取指定 ID 的红外深度传感器距离
  • 参数
    • id (int:[1, 4]):红外传感器的 ID
  • 返回值
    • distance_value:指定 ID 的红外传感器测得的距离值,单位 mm
  • 示例
    • IN: ir_distance_sensor distance 1 ?; :查询 1 号红外深度传感器测得的距离值
    • OUT: 1000 :当前查询红外深度传感器距离值为 1000 mm

舵机控制

舵机角度控制

IN: servo angle id <servo_id> angle <angle_value>

  • 描述
    • 设置舵机角度
  • 参数
    • servo_id (int:[1, 3]):舵机的 ID
    • angle_value (float:[-180, 180]):指定的角度,单位 °
  • 示例
    • servo angle id 1 angle 20; :控制 1 号舵机的角度为 20°
舵机速度控制

IN: servo speed id <servo_id> speed <speed_value>

  • 描述
    • 设置指定舵机的速度
  • 参数
    • servo_id (int:[1, 3]):舵机的 ID
    • speed_value (float:[-1800, 1800]):设置的速度值,单位 °/s
  • 示例
    • servo speed id 1 speed 20; :设置 1 号舵机的速度为 10°/s
舵机停止控制

IN: servo stop

  • 描述
    • 停止舵机运动
  • 示例
    • servo stop; :控制舵机停止运动
舵机角度查询

IN: servo angle id <servo_id> ?

  • 描述
    • 获取指定舵机的角度
  • 参数
    • servo_id (int:[1, 3]):舵机的 ID
  • 返回值
    • angle_value : 指定舵机的角度值
  • 示例
    • IN: servo angle id 1 ?; :获取 1 号舵机的角度值
    • OUT: 30 :当前查询舵机角度值为 30°

机械臂控制

机械臂相对位置运动控制

IN: robotic_arm move x <x_dist> y <y_dist>

  • 描述
    • 控制机械臂运动一段距离,当前位置为坐标原点
  • 参数
    • x_dist (float:[]) :x 轴运动距离,单位 cm
    • y_dist (float:[]) :y 轴运动距离,单位 cm
  • 示例
    • robotic_arm move x 5 y 5; :控制机械臂在 x 轴运动 5 cm,在 y 轴运动 5 cm
机械臂绝对位置运动控制

IN: robotic_arm moveto x <x_pos> y <y_pos>

  • 描述
    • 控制机械臂运动到某位置,机器人上电位置为坐标原点
  • 参数
    • x_pos (float:[]):x 轴运动到的坐标,单位 cm
    • y_pos (float:[]):y 轴运动到的坐标,单位 cm
  • 示例
    • robotic_arm moveto x 5 y 5; :控制机械臂 x 轴运动到 5 cm 的坐标位置,y 轴运动到 5 cm 的坐标位置
机械臂回中控制

IN: robotic_arm recenter

  • 描述
    • 控制机械臂回中
  • 参数
    • None
  • 示例
    • robotic_arm recenter; :控制机械臂回中
机械臂停止运动控制

IN: robotic_arm stop

  • 描述
    • 停止机械臂运动
  • 参数
    • None
  • 示例
    • robotic_arm stop; :停止机械臂运动
机械臂绝对位置查询

IN: robotic_arm position ?

  • 描述
    • 获取机械臂的位置
  • 参数
    • None
  • 返回值
    • <x_pos> <y_pos>: 机械臂的位置坐标
      • x_pos:x 轴的坐标,单位 cm
      • y_pos:y 轴的坐标,单位 cm
  • 示例
    • IN: robotic_arm position ?; :查询机械臂的位置
    • OUT:50 60 :当前查询机械臂的位置距离标定点 x 轴距离为 50 cm, y 轴距离为 60 cm

机械爪控制

机械爪张开运动控制

IN: robotic_gripper open [leve <level_num>]

  • 描述
    • 张开机械爪
  • 参数
    • level_num (int:[1,4]):机械爪张开的力度等级,取值范围[1,4]
  • 示例
    • robotic_gripper open 1; :控制机械臂以力度 1 打开
机械爪关闭运动控制

IN: robotic_gripper close [leve <level_num>]

  • 描述
    • 闭合机械爪
  • 参数
    • level_num (int:[1,4]):机械爪闭合的力度等级,取值范围[1,4]
  • 示例
    • robotic_gripper close 1; :控制机械臂以力度 1 关闭

注解

机械爪控制力度

机械爪控制力度 描述了机械爪在运动过程中的运动速度以及在堵转状态下最大夹取力度

力度越大,运动速度越快,夹取力越大;反之。

机械爪开合状态查询

IN: robotic_gripper status ?

  • 描述
    • 获取机械爪开合状态
  • 参数
    • None
  • 返回值
    • status : 机械爪当前的开合状态
      • 0 机械爪完全闭合
      • 1 机械爪既没有完全闭合,也没有完全张开
      • 2 机械爪完全张开
  • 示例
    • IN: robotic_gripper status ?; :获取机械爪的开合状态
    • OUT: 2 :当前查询的机械爪状态为张开

智能识别功能控制

智能识别功能属性控制

IN: AI attribute { [line_color <line_color>] [marker_color <marker_color>] [marker_dist <dist>] }

  • 描述
    • 智能识别功能属性控制
  • 参数
    • line_color (line_color_enum): 线识别颜色
    • marker_color (marker_color_enum): 视觉标签颜色
    • marker_dist (float:[0.5, 3]): 视觉标签最小有效距离,单位m
  • 示例
    • IN: AI attribute line_color red; :设置线识别的颜色为红色
智能识别功能推送控制

IN: AI push <attr> <switch>

  • 描述
    • 智能识别功能推送控制
    • 不同智能识别功能之间存在互斥关系,互斥的功能无法同时开启,若单次同时打开的功能集合中存在互斥关系的功能,则本次功能开启全部失败。关于互斥关系请参见:智能识别功能互斥关系
    • 暂不支持频率设置
    • 数据提送格式参见 智能识别功能推送数据
  • 参数
    • attr (AI_push_attr_enum): 智能识别功能枚举,部分参数之前不可同时打开
    • switch (switch_enum):当此处参数使用 on 时,表示打开对应属性的推送;当此处参数使用 off 时,表示关闭对应属性的推送
  • 示例
    • IN: AI push marker on line on; :打开线和视觉标签识别数据推送

注解

智能识别功能互斥关系

由于机器人计算资源有限,智能识别功能中存在互斥关系,互斥的智能功能无法同时开启。 我们将智能识别功能分为AB两组:

A people pose marker robot
B line

以上两组,任意一组内同时仅能开启一个功能,两组间可任意组合功能

智能识别功能推送数据

OUT: AI push <attr> <data>

  • 描述
    • 当用户使能智能识别功能推送后,机器人会以归固定的频率向用户推送相应信息
  • 参数
    • attr (AIi_push_attr_enum): 订阅的功能名称
    • data :订阅的属性数据
      • attrperson 时,内容为 <n> <x1> <y1> <w1> <h1> <x2> <y2> … <wn> <hn>
      • attrgesture 时 内容为 <n> <info1> <x1> <y1> <w1> <h1> <x2> <y2> … <wn> <hn>, info 含义请参见 AI_pose_id_enum
      • attrmarker 时,内容为 <n> <info1> <x1> <y1> <w1> <h1> <x2> <y2> … <wn> <hn>, info 含义请参见 AI_marker_id_enum
      • attrline 时,内容为 <n> <x1> <y1> <θ1> <c1> <x2> <y2> … <θ10n> <c10n>
      • attrrobot 时,内容为 <n> <x1> <y1> <w1> <h1> <x2> <y2> … <wn> <hn>
  • 示例
    • OUT: AI push person 1 0.5 0.5 0.3 0.7 : 当前识别到1个行人,坐标位于(0.5, 0.5),目标宽度为0.3,高度为0.7

注解

智能功能推送数据

智能识别功能推送数据中,n,x,y,w,h 均为通用数据,解释如下:

n : 识别到的目标数量

x : 识别到的目标中心点位于视野中的x坐标

y : 识别到的目标中心点位于视野中的y坐标

w : 识别到的目标宽度

h : 识别到的目标高度

线识别推送数据中,n, x, y, θ, c 解释如下:

n : 识别到线的数量,每条线分别存在10个点,详细点数据请参下

x : 线上点位于视野中的x坐标

y : 线上点位于视野中的y坐标

θ : 线上点的切线角角度

c : 线上点对应的曲线的曲率,取值范围 [0, 10], 0表示纯直线

以上 x,y,w,h 均为归一化的值,范围为[0, 1],坐标远点位于视野左上方

相机控制

相机曝光设置

IN: camera exposure <ev_level>

  • 描述
    • 相机曝光值设置
  • 参数
  • 示例
    • camera exposure small; :设置相机曝光值为小

视频流控制

视频流开启控制

IN: stream on

  • 描述
    • 打开视频流
    • 打开后,可从视频流端口接收到 H.264 编码的码流数据
  • 示例
    • stream on; :打开视频流
视频流关闭控制

IN: stream off

  • 描述
    • 关闭视频流
    • 关闭视频流后,H.264 编码的码流数据将会停止输出
  • 示例
    • stream off; :关闭视频流

音频流控制

音频流开启控制

IN: audio on

  • 描述
    • 打开音频流
    • 关闭音频流后,可以从音频流端口接收到 Opus 编码的音频流数据
  • 示例
    • audio on; :打开音频流
音频流关闭控制

IN: audio off

  • 描述
    • 关闭音频流
    • 关闭音频流后,Opus 编码的音频流数据将会停止输出
  • 示例
    • audio off; :关闭音频流

IP 广播

OUT: robot ip <ip_addr>

  • 描述
    • 当未与机器人建立连接时,可以从 IP 广播端口接收到此消息,连接成功后,该消息停止广播
    • 描述当前机器人的 IP 地址,适用于与机器人在同一局域网内,但未知机器人 IP 信息的情况
  • 参数
    • ip_addr : 机器人当前 IP 地址
  • 示例
    • robot ip 192.168.1.102 : 机器人当前的 IP 地址为 192.168.1.102

数据说明

switch_enum
  • on : 打开
  • off : 关闭
mode_enum
  • chassis_lead : 云台跟随底盘模式
  • gimbal_lead : 底盘跟随云台模式
  • free : 自由模式
chassis_push_attr_enum
  • position : 底盘位置
  • attitude : 底盘姿态
  • status : 底盘状态
gimbal_push_attr_enum
  • attitude 云台姿态
armor_event_attr_enum
  • hit : 装甲被敲击
sound_event_attr_enum
  • applause : 掌声
led_comp_enum
  • all : 所有 LED 灯
  • top_all : 云台所有 LED 灯
  • top_right : 云台右侧 LED 灯
  • top_left : 云台左侧 LED 灯
  • bottom_all : 底盘所有 LED 灯
  • bottom_front : 底盘前侧 LED 灯
  • bottom_back : 所有后侧 LED 灯
  • bottom_left : 所有左侧 LED 灯
  • bottom_right : 所有右侧 LED 灯
led_effect_enum
  • solid : 常亮效果
  • off : 熄灭效果
  • pulse : 呼吸效果
  • blink : 闪烁效果
  • scrolling : 跑马灯
line_color_enum
  • red : 红色
  • blue : 蓝色
  • green : 绿色
marker_color_enum
  • red : 红色
  • blue : 蓝色
ai_push_attr_enum
  • person : 行人
  • gesture : 姿势
  • line :线
  • marker : 视觉标签
  • robot : 机器人
ai_pose_id_enum
  • 4 : 正V手势
  • 5 : 倒V手势
  • 6 : 拍照手势
ai_marker_id_enum
  • 1 : 停止
  • 4 : 左转
  • 5 : 右转
  • 6 : 前进
  • 8 : 红心
  • 10 - 19 : 数字 0 - 9
  • 20 - 45 : 字母 A - Z
camera_ev_enum
  • default : 默认值
  • small : 小
  • medium : 中
  • large : 大

Python 编程介绍

介绍

本章介绍的 Python 编程指的是使用设备连接 EP 机器人后,进入 App 实验室进行 Python 编程。

在 Python 编程界面,允许玩家基于 Python 3.6.6 版本的基础语法完成 Python 编程,并可以参考官方提供的《RoboMaster EP 编程模块手册》和本网站 Python API,调用 RoboMaster EP 提供的编程接口去编写自己的 Python 程序,同时生成的 Python 程序可被装配成自主程序或者自定义技能。

RoboMaster EP 的多机通信接口让多台机器人通过 Python 编程相互通信,实现多机实时互动。 EP 支持编程自定义 UI 系统,通过 Python 编写虚拟控件,自由设计交互界面,拓展无限应用可能。

界面

为了方便代码编辑,一般会使用 PC 端的 App 进行 Python 编程。

_images/python_env.png

PC 端 Python 编程界面

Python 功能介绍

多机通信系统

多机通信系统是一种基于局域网实现多台机器人之间相互通信的功能,为用户提供了多台机器人协同工作,多台机器人编队表演等功能的实现的可能。

使用时需要将所有目标机器人加入到同一个局域网内,并使用官方提供的Python API进行编程,来沟通机器人之间的通信机制,进一步实现具体的功能。

Python API 请参考 自定义UI系统

用户自定义 UI 系统

自定义 UI 系统是用户通过自己编写的程序生成自定义的 UI 控件来拓展程序的输入和输出的一种方式。

我们编程时很重要的一部分工作是处理输入和输出,对我们的机器人来说,程序输出可以是底盘、云台、水弹枪等模块的动作,也可以是灯光、音效等的表现,输入的途径则有初始的变量,机器人的视觉识别、掌声识别、装甲板打击检测,手机陀螺仪等。现在我们可以通过自定义 UI 系统与生成的 UI 控件进行交互达到输入的目的,也可以将程序的处理结果通过 UI 控件来进行信息的输出。

我们可以在 RoboMaster app 中编写 Python 程序,调用自定义 UI 系统的相关接口,来生成 UI 控件,绑定控件的事件回调。在实验室中完成程序的编写和调试后,可以将程序装配成自定义技能,在单机驾驶或者多人竞技中释放出来。

Python API 请参考 自定义UI系统

Python API

机器人

robot_ctrl.get_battery_percentage()
描述:

机器人电池电量获取

参数:

void – 无

返回:

电池电量百分比 (0, 100]

示例:

>> robot_ctrl.get_battery_percentage()

<< 10

示例说明:

当前机器人电量为10%

多机通信

multi_comm_ctrl.set_group(send_group, recv_group_list)
描述:

设置机器的组号为 send_group ,机器可以接收来自 recv_group_list 中注册的组号的消息。如果不使用 recv_group_list 参数,默认接收组号 0 的消息

参数:
  • send_group (int) – 当前机器的发送组号,默认组号为 0
  • recv_group_list (list/tuple) – 当前接收消息的组别列表,类型可以为列表或元组
返回:

示例:

multi_comm_ctrl.set_group(1, (1,2,3))

示例说明:

设置当前发送组号为 1, 接收组号 1,2,3 的消息,若接收组别包含发送组别,则会接收到自己发送的消息

multi_comm_ctrl.send_msg(msg, group)
描述:

通过多机通信发送消息,可以单独设置该消息的发送组号

参数:
  • msg (int) – 需要发送的消息
  • group (int) – 可选参数,指定当前消息发送组号,不指定则默认使用之前设置的组号
返回:

示例:

multi_comm_ctrl.send_msg('RoboMaster EP', 3)

示例说明:

向组号 3 发送消息 'RoboMaster EP'

multi_comm_ctrl.recv_msg(timeout)
描述:接收消息(当没有注册`recv_callback`时生效),可设置超时时间
参数:timeout (int) – 等待时间,接收函数等待的时间,精确度为 1 秒,默认为 72 秒
返回:<msg_group>, <msg> 消息发送方的组号和消息内容
示例:group, recv_msg = multi_comm_ctrl.recv_msg(30)
示例说明:接收消息,等待时间为 30 秒,group 为信息发送方的组号,msg 为收到的消息内容
multi_comm_ctrl.register_recv_callback(callback)
描述:注册接收消息的回调函数,当接收到信息后,自动执行回调函数
参数:callback (function) – 需要注册的回调函数, 回调函数原型为 def callback(msg),其中 msg 参数类型为元组 (msg_group, msg)
返回:
示例:
1
2
3
4
5
6
#定义一个函数,并将其注册为接收消息的回调函数

def recv_callback(msg):
    pass

multi_comm_ctrl.register_recv_callback(recv_callback)

提示

模块说明请参考 多机通信

自定义 UI 系统

Common

本部分方法适用于除 Stage 外所有自定义 UI 控件,因此单独拿出来介绍。

common_object.set_active(status)
描述:控制当前控件是否显示
参数:status (bool) – 控件的活动状态,True 表示显示当前控件,False 表示隐藏当前控件
返回:
示例:my_Slider.set_active(Flase)
示例说明:设置 my_Slider 控件为隐藏状态
common_object.get_active()
描述:获取当前控件的显示状态
参数:void – 无
返回:bool, 表示控件的显示状态
示例:status = my_Slider.get_active()
示例说明:获取 my_Slider 控件的显示状态,赋值给 status 变量
common_object.set_name(name)
描述:设置当前控件的名字
参数:name (string) – 控件的名字
返回:
示例:my_Dropdown.set_name('my_dropdown')
示例说明:设置 my_Dropdown 控件的名字为『my_dropdown』
common_object.get_name()
描述:获取当前控件的名字
参数:void – 无
返回:string,表示控件的名字
示例:name = my_Dropdown.get_name()
示例说明:获取 my_Dropdown 控件的名字,赋值给 name 变量
common_object.set_position(x, y)
描述:

设置控件的位置坐标,原点在屏幕的中心位置

参数:
  • x (int) – 控件的横坐标,取值为屏幕上实际像素的位置,0 点在屏幕水平中心位置,向右为正方向
  • y (int) – 控件的纵坐标,取值为屏幕上实际像素的位置,0 点在屏幕垂直中心位置,向上为正方向
返回:

示例:

my_Text.set_position(-200, 500)

示例说明:

设置 my_Text 控件的坐标为 (-200,500)

common_object.get_position()
描述:获取控件的位置坐标
参数:void – 无
返回:[x,y],表示控件的位置
示例:pos = my_Text.get_position()
示例说明:获取 my_Text 控件的位置,赋值给变量 pos,pos 为一个列表
common_object.set_size(w, h)
描述:

设置控件的大小

参数:
  • w (int) – 控件的宽度
  • h (int) – 控件的高度
返回:

示例:

my_Button.set_size(300, 200)

示例说明:

设置 my_Button 控件的宽度为 300,高度为 200

common_object.get_size()
描述:获取控件的大小
参数:void – 无
返回:[w,h], 表示控件的大小
示例:size = my_Button.get_size()
示例说明:获取 my_Button 控件的大小,赋值给变量 size,size 为一个列表
common_object.set_rotation(degree)
描述:设置控件的旋转角度
参数:degree (int) – 控件的旋转角度,范围为 [0, 360],正值为顺时针旋转,负值为逆时针旋转
返回:
示例:my_Button.set_rotation(90)
示例说明:设置 my_Button 控件顺时针旋转 90 度
common_object.get_rotation()
描述:获取控件的旋转角度
参数:void – 无
返回:int, 表示控件的旋转角度,范围为 [0, 360],正值为顺时针旋转,负值为逆时针旋转
示例:degree = my_Button.get_rotation()
示例说明:获取 my_Button 控件的旋转角度,赋值给变量 degree
common_object.set_privot(x, y)
描述:

设置控件的锚点坐标,输入参数是归一化参数,原点位于控件的左下角,控件的锚点默认为控件中心即 (0.5,0.5),控件的位置和旋转均以锚点作为控制点

参数:
  • x (int) – 锚点的 x 坐标,范围为 [0, 1],向右为正方向
  • y (int) – 锚点的 y 坐标,范围为 [0, 1],向上为正方向
返回:

示例:

my_Button.set_privot(0, 1)

示例说明:

设置控件的锚点为控件的左上角

common_object.get_privot()
描述:获取控件的锚点坐标
参数:void – 无
返回:[x,y],表示控件的锚点坐标
示例:privot = my_Button.get_privot()
示例说明:获取控件的锚点坐标,赋值给变量 privot,privot 为一个列表
common_object.set_order(order)
描述:设置控件的显示优先级,当多个控件重叠时,优先级高的控件在上层,数字越大优先级越高
参数:order (int) – 控件的指定优先级,控件重叠时优先级高的优先显示
返回:
示例:my_Button.set_order(8)
示例说明:将控件的显示优先级设置为 8,当控件重叠时,低于此优先级的控件将被覆盖
common_object.get_order()
描述:获取控件的显示优先级
参数:void – 无
返回:int,表示控件的显示优先级
示例:order = my_Button.get_order()
示例说明:获取 my_Button 控件的显示优先级,赋值给变量 order
common_object.callback_register(event, callback)
描述:

注册控件事件触发的回调函数,当控件检测到相应的事件后,执行注册的回调函数

参数:
  • event (string) –

    指定回调函数的触发事件

    各控件可注册的事件如下:

    • Button 控件:
      • on_click 一次按下松开按钮的过程, 在松开按钮的时候触发该事件
      • on_press_down 按下按钮的时候触发该事件
      • on_press_up 松开按钮的时候触发该事件
    • Toggle 控件:
      • on_value_changed 值发生改变的时候触发该事件,回调函数中的 args 参数为 bool,表示该 Toggle 控件值发生改变后的值
    • Dropdown 控件:
      • on_value_changed 值发生改变的时候触发该事件,回调函数中的 args 参数为 int,表示该 Dropdown 控件值发生改变后的选中索引
    • Text 控件:
      • 无触发事件
    • InputField 控件:
      • on_value_changed 值发生改变的时候触发该事件,回调函数中的 args 参数为 string,表示该 InputField 控件值发生改变后的值
  • callback (function) – 需要注册的回调函数,回调函数的统一签名为: def callback(widget,*args,**kw): ,其中 widget 为触发事件的控件引用,args,kw为参数.
返回:

示例 1:
1
2
3
4
5
6
# 当 my_Button 控件被点击后,打印信息到控制台上,机器人会开枪射击一次

def button_callback(widget,*args,**kw):
    print('the button is clicked and the button's name is '+ widget.get_name())
    gun_ctrl.fire_once()
my_Button.callback_register('on_click',button_callback)
示例 2:
1
2
3
4
5
6
7
# 当 my_Toggle 控件被点击后,值会发生改变,打印信息到控制台上,机器人会播放声音

def toggle_callback(widget,*args,**kw):
    print("the toggle's value is changed and the toggle's name is "+ widget.get_name())
    print("the toggle's value now is "+ str(args))
    media_ctrl.play_sound(rm_define.media_sound_recognize_success)
my_Toggle.callback_register('on_value_changed',toggle_callback)
示例 3:
1
2
3
4
5
6
7
# 当点击 my_Dropdown 控件改变其选中的值,值会发生改变,打印信息到控制台上,机器人会播放声音

def dropdown_callback(widget,*args,**kw):
    print("the dropdown's value is changed and the dropdown's name is "+ widget.get_name())
    print("the dropdown's value now is "+ str(args))
    media_ctrl.play_sound(rm_define.media_sound_solmization_1A)
my_Dropdown.callback_register('on_value_changed',dropdown_callback)
示例 4:
1
2
3
4
5
6
# 当点击 my_InputField 控件改变其选中的值,值会发生改变,打印信息到控制台上

def input_field_callback(widget,*args,**kw):
    print("the input_field's value is changed and the input_field's name is "+ widget.get_name())
    print("the input_field's value now is "+ str(args))
my_InputField.callback_register('on_value_changed',input_field_callback)

Stage

系统初始化时会自动创建一个 Stage 类的对象 stage ,直接使用即可,不需要用户自己创建。

stage.add_widget(widget_obj)
描述:将参数中的控件添加到 UI 界面中
参数:widget_obj (object) – 需要添加进 UI 界面的控件对象
返回:
示例:
1
2
3
4
#创建一个 Button 对象,并将其添加进 UI 界面

my_button = Button()
stage.add_widget(my_button)
stage.remove_widget(widget_obj)
描述:从 UI 界面移除参数传入的控件
参数:widget_obj (object) – 需要从 UI 界面移除的控件
返回:
示例:stage.remove_widget(my_button)
示例说明:从 UI 界面中移除控件 my_button

Button

Button 控件用于响应来自用户的点击来启动或确认操作。

button_object.set_text(content, [color_r, color_g, color_b, color_a, ]align, size)
描述:

设置按钮对象的文字属性

参数:
  • content (string) – 按钮上显示的字符串内容
  • [color_r, color_g, color_b, color_a] (list) – 可选参数,需要显示的字符串的颜色,参数分别为显示颜色 r 值、b 值,g 值,透明度,取值范围都为 [0, 255]
  • align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
  • size (int) – 显示文字的字号大小
返回:

示例:

my_Button.set_text(120, 120, 120, 255, text_anchor.upper_left, 12)

示例说明:

设置文字颜色的 rgb 值为(120, 120, 120),透明度为 255,文字对齐方式为顶端左对齐,字号大小为 12 号

button_object.set_text_color(r, g, b, a)
描述:

设置文字的颜色

参数:
  • r (int) – 文字颜色的 r 值,范围为 [0, 255]
  • g (int) – 文字颜色的 g 值,范围为 [0, 255]
  • b (int) – 文字颜色的 b 值,范围为 [0, 255]
  • a (int) – 文字颜色的透明度,范围为 [0, 255]
返回:

示例:

my_button.set_text_color(120, 120, 120, 200)

示例说明:

设置文字颜色的 rgb 值为(120, 120, 120),透明度为 200

button_object.set_text_align(align)
描述:设置文字的对齐方式
参数:align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详见表格 align
返回:
示例:my_button.set_text_align(text_anchor.upper_left)
示例说明:设置文字的对齐方式为顶端左对齐
button_object.set_text_size(size)
描述:设置文字的字号大小
参数:size (int) – 文字的字号值
返回:
示例:my_button.set_text_size(12)
示例说明:设置文字的字号为 12 号
button_object.set_background_color(r, g, b, a)
描述:

设置按钮的背景色

参数:
  • r (int) – 字体颜色的 r 值,范围为 [0, 255]
  • g (int) – 字体颜色的 g 值,范围为 [0, 255]
  • b (int) – 字体颜色的 b 值,范围为 [0, 255]
  • a (int) – 字体颜色的透明度,范围为 [0, 255]
返回:

示例:

my_button.set_background_color(200, 200, 200, 230)

示例说明:

设置背景色的 rgb 值为 (200, 200, 200),透明度为 230

Toggle

Toggle 控件用于在屏幕上绘制一个开关,通过控制开关的开启与闭合来执行一些具体的操作。

toggle_object.set_text(string, [color_r, color_g, color_b, color_a, ]align, size)
描述:

设置控件的显示文字

参数:
  • string (string) – 控件上显示的字符串内容
  • [color_r, color_g, color_b, color_a] (list) – 可选参数,需要显示的字符串的颜色,参数分别为显示颜色 r 值、b 值、g 值、透明度,取值范围都为 [0, 255]
  • align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
  • size (int) – 显示文字的字号大小
返回:

示例:

my_Toggle.set_text(120, 120, 120, 200, text_anchor.upper_left, 12)

示例说明:

设置文字的 rgb 值为(120, 120, 120),透明度为 200,字体对齐方式为顶端左对齐,字号大小为 12 号

toggle_object.set_text_color(r, g, b, a)
描述:

设置文字的颜色

参数:
  • r (int) – 文字颜色的 r 值,范围为 [0, 255]
  • g (int) – 文字颜色的 g 值,范围为 [0, 255]
  • b (int) – 文字颜色的 b 值,范围为 [0, 255]
  • a (int) – 文字颜色的透明度,范围为 [0, 255]
返回:

示例:

my_Toggle.set_text_color(120, 120, 120, 200)

示例说明:

设置字体的 rgb 值为(120, 120, 120),透明度为 200

toggle_object.set_text_align(align)
描述:设置文字的对齐方式
参数:align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
返回:
示例:my_Toggle.set_text_align(text_anchor.upper_left)
示例说明:设置字体的对齐方式为顶端左对齐
toggle_object.set_text_size(size)
描述:设置文字的字号大小
参数:size (int) – 文字的字号值
返回:
示例:my_Toggle.set_text_size(12)
示例说明:设置文字的字号为 12 号
toggle_object.set_background_color(r, g, b, a)
描述:

设置控件的背景色

参数:
  • r (int) – 背景颜色的 r 值,范围为 [0, 255]
  • g (int) – 背景颜色的 g 值,范围为 [0, 255]
  • b (int) – 背景颜色的 b 值,范围为 [0, 255]
  • a (int) – 背景颜色的透明度,[0, 255]
返回:

示例:

my_Toggle.set_background_color(200, 200, 200, 230)

示例说明:

设置背景色的 rgb 值为 (200, 200, 200),透明度为 230

toggle_object.set_checkmark_color(r, g, b, a)
描述:

设置控件选中图标的颜色

参数:
  • r (int) – 图标颜色的 r 值,范围为 [0, 255]
  • g (int) – 图标颜色的 g 值,范围为 [0, 255]
  • b (int) – 图标颜色的 b 值,范围为 [0, 255]
  • a (int) – 图标颜色的透明度,范围为 [0, 255]
返回:

示例:

my_Toggle.set_checkmark_color(200, 200, 200, 230)

示例说明:

设置选中图标的 rgb 值为 (200, 200, 200),透明度为 230

toggle_object.set_is_on(status)
描述:设置控件的状态
参数:status (bool) – 设置控件是否为打开状态,True 表示打开,False 表示关闭
返回:
示例:my_Toggle.set_is_on(True)
示例说明:设置 Toggle 控件为打开状态

Text

Text 控件用于显示文本

text_object.set_text(string, [color_r, color_g, color_b, color_a, ]align, size)
描述:

设置控件的文字属性

参数:
  • string (string) – 需要显示的字符串内容
  • [color_r, color_g, color_b, color_a] (list) – 可选参数,需要显示的字符串的颜色,参数分别为显示颜色 r 值、b 值、g 值,透明度,取值范围都为 [0, 255]
  • align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
  • size (int) – 显示文字的字号大小
返回:

示例:

my_Text.set_text(120, 120, 120, 200, text_anchor.upper_left, 12)

示例说明:

设置文字颜色的 rgb 值为(120, 120, 120),透明度为 200,字体对齐方式为顶端左对齐,字号大小为 12 号

text_object.set_text_color(r, g, b, a)
描述:

设置控件的文字颜色

参数:
  • r (int) – 文字颜色的 r 值,范围为 [0, 255]
  • g (int) – 文字颜色的 g 值,范围为 [0, 255]
  • b (int) – 文字颜色的 b 值,范围为 [0, 255]
  • a (int) – 文字颜色的透明度,范围为 [0, 255]
返回:

示例:

my_Text.set_text_color(120, 120, 120, 200)

示例说明:

设置文字的 rgb 值为(120, 120, 120),透明度为 200

text_object.set_text_align(align)
描述:设置文字的对齐方式
参数:align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
返回:
示例:my_Text.set_text_align(text_anchor.upper_left)
示例说明:设置文字的对齐方式为顶端左对齐
text_object.set_text_size(size)
描述:设置文字的字号大小
参数:size (int) – 文字的字号值
返回:
示例:my_Text.set_text_size(12)
示例说明:设置文字的字号为 12 号
text_object.set_border_active(active)
描述:是否显示文字边框
参数:active (bool) – 是否显示文字边框,True 表示显示边框,False 表示不显示边框
返回:
示例:my_Text.set_border_active(True)
示例说明:显示文字边框
text_object.set_background_color(r, g, b, a)
描述:

设置控件的背景色

参数:
  • r (int) – 背景颜色的 r 值,范围为 [0, 255]
  • g (int) – 背景颜色的 g 值,范围为 [0, 255]
  • b (int) – 背景颜色的 b 值,范围为 [0, 255]
  • a (int) – 背景颜色的透明度,范围为 [0, 255]
返回:

示例:

my_Text.set_background_color(200, 200, 200, 230)

示例说明:

设置背景色的 rgb 值为 (200, 200, 200),透明度为 230

text_object.set_background_active(active)
描述:是否显示文字背景
参数:active (bool) – 是否显示背景,True 表示显示背景,False 表示不显示背景
返回:
示例:my_Text.set_background_active(True)
示例说明:显示文字背景
text_object.append_text(content)
描述:向 Text 控件中增加文本
参数:content (string) – 需要向 Text 中增加的文本
返回:
示例:my_Text.append_text('RoboMaster EP')
示例说明:向 Text 中增加的文字 RoboMaster EP
align
text_anchor.upper_left 顶端左对齐
text_anchor.upper_center 顶端居中对齐
text_anchor.upper_right 顶端右对齐
text_anchor.middle_left 中间左对齐
text_anchor.middle_center 中间居中对齐
text_anchor.middle_right 中间右对齐
text_anchor.lower_left 底端左对齐
text_anchor.lower_center 底端居中对齐
text_anchor.lower_right 底端右对齐

InputField

InputField 控件用于接收用户输入的文本信息

inputfield_object.set_text(string, [color_r, color_g, color_b, color_a, ]align, size)
描述:

设置输入框对象中的的文字属性

参数:
  • string (string) – 需要显示的字符串内容
  • [color_r, color_g, color_b, color_a] (list) – 可选参数,需要显示的字符串的颜色,参数分别为显示颜色 r 值、b 值,g 值,透明度,取值范围都为[0, 255]
  • align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
  • size (int) – 显示文字的字号大小
返回:

示例:

my_InputField.set_text('Hello RoboMaster',120, 120, 120, 200, text_anchor.upper_left, 12)

示例说明:

设置字体的 rgb 值为(120, 120, 120),透明度为 200 ,字体对齐方式为顶端左对齐,字号大小为 12 号

input_field_object.set_text_color(r, g, b, a)
描述:

设置文字的颜色

参数:
  • r (int) – 文字颜色的 r 值,范围为[0, 255]
  • g (int) – 文字颜色的 g 值,范围为[0, 255]
  • b (int) – 文字颜色的 b 值,范围为[0, 255]
  • a (int) – 文字颜色的透明度, 范围为[0, 255]
返回:

示例:

my_button.set_text_color(120, 120, 120, 200)

示例说明:

设置字体的 rgb 值为(120, 120, 120),透明度为 200

input_field_object.set_text_align(align)
描述:设置控件中文字的对齐方式
参数:align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
返回:
示例:my_Input_field.set_text_align(text_anchor.upper_left)
示例说明:设置文字的对齐方式为顶端左对齐
input_field_object.set_text_size(size)
描述:设置控件中文字的字号大小
参数:size (int) – 文字的字号值
返回:
示例:my_Input_field.set_text_size(12)
示例说明:设置文字的字号为 12 号
input_field_object.set_background_color(r, g, b, a)
描述:

设置控件的背景色

参数:
  • r (int) – 背景颜色的 r 值,范围为[0, 255]
  • g (int) – 背景颜色的 g 值,范围为[0, 255]
  • b (int) – 背景颜色的 b 值,范围为[0, 255]
  • a (int) – 背景颜色的透明度,[0, 255]
返回:

示例:

my_Input_field.set_background_color(200, 200, 200, 230)

示例说明:

设置背景色的 rgb 值为(200, 200, 200) ,透明度为 230

input_field_object.set_hint_text(string, [color_r, color_g, color_b, color_a, ]align, size)
描述:

设置控件中的提示文字的属性

参数:
  • string (string) – 需要显示的字符串内容
  • [color_r, color_g, color_b, color_a] (list) – 可选参数,需要显示的字符串的颜色,参数分别为显示颜色 r 值、b 值,g 值,透明度,取值范围都为[0, 255]
  • align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
  • size (int) – 显示文字的字号大小
返回:

示例:

my_Input_field.set_hint_text(120, 120, 120, 200, text_anchor.upper_left, 12)

示例说明:

设置提示文字的 rgb 值为(120, 120, 120),透明度为 200 ,字体对齐方式为顶端左对齐,字号大小为 12 号

input_field_object.set_hint_text_color(r, g, b, a)
描述:

设置控件提示文字的颜色

参数:
  • r (int) – 文字颜色的 r 值,范围为[0, 255]
  • g (int) – 文字颜色的 g 值,范围为[0, 255]
  • b (int) – 文字颜色的 b 值,范围为[0, 255]
  • a (int) – 文字颜色的透明度, 范围为[0, 255]
返回:

示例:

my_Input_field.set_text_color(120, 120, 120, 200)

示例说明:

设置提示文字的 rgb 值为(120, 120, 120),透明度为 200

input_field_object.set_hint_text_align(align)
描述:设置提示文字的对齐方式
参数:align (enum) – 可选参数,枚举类型,需要显示文字的对齐方式,详细见表格 align
返回:
示例:my_Input_field.set_text_align(text_anchor.upper_left)
示例说明:设置提示文字的对齐方式为顶端左对齐
input_field_object.set_hint_text_size(size)
描述:设置提示文字的字号大小
参数:size (int) – 文字的字号值
返回:
示例:my_Input_field.set_text_size(12)
示例说明:设置 hint 对象中文字的字号为 12 号

提示

功能说明请参考 用户自定义 UI 系统

发射器

ir_blaster_ctrl.set_fire_count(count)
描述:设置红外光束的发射频率,即每秒射出的红外光束次数
参数:color_enum (int) – 发射频率,即每秒射出的红外光束次数,范围为[1:8]
返回:
示例:ir_blaster_ctrl.set_fire_count(4)
示例说明:设置红外光束的发射频率为 4
ir_blaster_ctrl.fire_once()
描述:控制发射器只发射一次红外光束
参数:void – 无
返回:
示例:ir_blaster_ctrl.fire_once()
示例说明:控制发射器只发射一次红外光束
ir_blaster_ctrl.fire_continuous()
描述:控制发射器持续发射红外光束
参数:void – 无
返回:
示例:ir_blaster_ctrl.fire_continuous()
示例说明:控制发射器持续发射红外光束
ir_blaster_ctrl.stop()
描述:停止发射红外光束
参数:void – 无
返回:
示例:ir_blaster_ctrl.stop()
示例说明:停止发射红外光束

机械爪

gripper_ctrl.open()
描述:控制机械爪打开
参数:void – 无
返回:
示例:gripper_ctrl.open()
示例说明:控制机械爪打开
gripper_ctrl.close()
描述:控制机械爪关闭
参数:void – 无
返回:
示例:gripper_ctrl.close()
示例说明:控制机械爪关闭
gripper_ctrl.stop()
描述:控制机械爪停止运动
参数:void – 无
返回:
示例:gripper_ctrl.stop()
示例说明:控制机械爪停止运动
gripper_ctrl.update_power_level(level)
描述:设置机械爪力度档位
参数:level (int) – 机械爪的力度档位,范围为[1:4]档,默认为 1
返回:
示例:gripper_ctrl.update_power_level(1)
示例说明:设置机械爪力度档位为 1
gripper_ctrl.is_closed()
描述:获取机械爪夹紧状态
参数:void – 无
返回:机械爪夹紧状态,若机械爪夹紧则返回 true,否则返回 false
返回类型:bool
示例:ret = gripper_ctrl.is_closed()
示例说明:获取机械爪夹紧状态
gripper_ctrl.is_open()
描述:获取机械爪张开状态
参数:void – 无
返回:机械爪张开状态,若机械爪完全张开则返回 true,否则返回 false
返回类型:bool
示例:ret = gripper_ctrl.is_open()
示例说明:获取机械爪张开状态

提示

模块说明请参考 机械臂与机械爪

机械臂

robotic_arm_ctrl.move(x, y, wait_for_complete=True)
描述:

设置机械臂运动的相对位置

参数:
  • x (int32) – 设置机械臂水平运动的距离,正数为向前运动,负数为向后运动,精确度为 1 mm
  • y (int32) – 设置机械臂垂直运动的距离,正数为向上运动,负数为向下运动,精确度为 1 mm
  • wait_for_complete (bool) – 是否等待执行完成,默认为 True
返回:

示例:

robotic_arm_ctrl.move(40, 50, True)

示例说明:

设置机械臂向前移动 20 mm,向上移动 30 mm,等待执行完成

robotic_arm_ctrl.moveto(x, y, wait_for_complete=True)
描述:

设置机械臂运动到绝对坐标

参数:
  • x (int32) – 设置机械臂水平运动的坐标值,精确度为 1 mm
  • y (int32) – 设置机械臂垂直运动的坐标值,精确度为 1 mm
  • wait_for_complete (bool) – 是否等待执行完成,默认为 True
返回:

示例:

robotic_arm_ctrl.moveto(40, 50, True)

示例说明:

设置机械臂移动到(x=40mm,y=50mm)的绝对坐标,等待执行完成

robotic_arm_ctrl.get_position()
描述:获取机械臂位置
参数:void – 无
返回:机械臂的绝对坐标,精确度为 1 mm
返回类型:列表[x, y], x 和 y 为 int32 类型
示例:[x, y] = robotic_arm_ctrl.get_position()
示例说明:获取机械臂的绝对坐标
robotic_arm_ctrl.recenter()
描述:设置机械臂回中
参数:void – 无
返回:
示例:robotic_arm_ctrl.recenter()
示例说明:设置机械臂回中

提示

模块说明请参考 机械臂与机械爪

舵机

servo_ctrl.get_angle(servo_id)
描述:获取舵机旋转角度
参数:servo_id (uint8) – 舵机编号,范围为[1:4]
返回:舵机角度,精确度为 0.1 度
返回类型:int32
示例:angle = servo_ctrl.get_angle(1)
示例说明:获取编号为 1 的舵机旋转角度
servo_ctrl.set_angle(servo_id, angle, wait_for_complete=True)
描述:

设置舵机旋转角度

参数:
  • servo_id (uint8) – 舵机编号,范围为[1:4]
  • angle (int32) – 旋转角度,精确度为 0.1 度,正数为顺时针旋转,负数为逆时针旋转
  • wait_for_complete (bool) – 是否等待执行完成,默认为 True
返回:

示例:

servo_ctrl.set_angle(1, 900, True)

示例说明:

设置编号为 1 的舵机顺时针旋转 90°,等待执行完成

servo_ctrl.recenter(servo_id, wait_for_complete=True)
描述:

设置舵机回中

参数:
  • servo_id (uint8) – 舵机编号,范围为[1:4]
  • wait_for_complete (bool) – 是否等待执行完成,默认为 True
返回:

示例:

servo_ctrl.recenter(1, True)

示例说明:

设置编号为 1 的舵机回中,等待执行完成

servo_ctrl.set_speed(servo_id, speed)
描述:

设置舵机旋转速度

参数:
  • servo_id (uint8) – 舵机编号,范围为[1:4]
  • speed (int32) – 旋转速度,精确度为 1 度/秒,正数为顺时针旋转,负数为逆时针旋转
返回:

示例:

servo_ctrl.set_speed(1, 5)

示例说明:

设置编号为 1 的舵机顺时针旋转,旋转速度为 5 度/秒

提示

模块说明请参考 舵机

智能

vision_ctrl.marker_detection_color_set(color_enum)
描述:设置视觉标签识别颜色
参数:color_enum – 标签颜色类型,详细见表格 color_enum
返回:
示例:vision_ctrl.marker_detection_color_set(rm_define.marker_detection_color_red)
示例说明:设置视觉标签识别颜色为红色
color_enum
rm_define.marker_detection_color_red 红色
rm_define.marker_detection_color_green 绿色
rm_define.marker_detection_color_blue 蓝色

装甲板

def ir_hit_detection_event(msg):
描述:当检测到机器人受到红外光束攻击时,运行函数内程序
参数:msg – 函数内部的消息参数
返回:
示例:
1
2
3
4
#当检测到机器人受到红外光束攻击时,运行函数内程序

def ir_hit_detection_event(msg):
    pass
armor_ctrl.cond_wait(condition_enum)
描述:等待机器人受到红外光束攻击时,执行下一条指令
参数:condition_enum – 事件类型,rm_define.cond_ir_hit_detection 表示机器人受到红外光束攻击
返回:
示例:armor_ctrl.cond_wait(rm_define.cond_ir_hit_detection)
示例说明:等待机器人受到红外光束攻击时,执行下一条指令
armor_ctrl.check_condition(condition_enum)
描述:判断机器人是否受到红外光束攻击
参数:condition_enum – 事件类型,rm_define.cond_ir_hit_detection 表示机器人受到红外光束攻击
返回:机器人是否受到红外光束攻击,受到攻击时返回真,否则返回假。
返回类型:bool
示例:if armor_ctrl.check_condition(rm_define.cond_ir_hit_detection):
示例说明:如果机器人受到红外光束攻击时,执行下一条指令

红外深度传感器

ir_distance_sensor_ctrl.enable_measure(port_id)
描述:开启红外深度传感器测距功能
参数:port_id (int) – 红外深度传感器模块编号,范围为[1:4]
返回:
示例:ir_distance_sensor_ctrl.enable_measure(1)
示例说明:开启 1 号红外深度传感器测距功能
ir_distance_sensor_ctrl.disable_measure(port_id)
描述:关闭红外深度传感器测距功能
参数:port_id (int) – 红外深度传感器模块编号,范围为[1:4]
返回:
示例:ir_distance_sensor_ctrl.disable_measure(1)
示例说明:关闭 1 号红外深度传感器测距功能
ir_distance_sensor_ctrl.get_distance_info(port_id)
描述:获取红外深度传感器测距信息
参数:port_id (int) – 红外深度传感器模块编号,范围为[1:4]
返回:红外深度传感器前方障碍物的距离,精确度为 1 cm
返回类型:uint16
示例:ir_distance_sensor_ctrl.get_distance_info(1)
示例说明:获取 1 号红外深度传感器测距信息
def ir_distance_[port_id]_[compare_type]_[dist]_event(msg):
描述:

当检测到红外深度传感器模块前方障碍物距离满足条件时,运行函数内程序

参数:
  • port_id (int) – 红外深度传感器模块编号,范围为[1:4]
  • compare_type – 比较类型,可以为 eq, ge, gt, le, lt, 分别表示等于,大于等于,大于,小于等于,小于
  • dist – 用于比较的距离,精确度为 1 cm,范围为 5~500 cm,误差率为 5%
返回:

示例:
1
2
3
4
#当检测到 1 号红外深度传感器前方障碍物距离小于 10 cm 时,运行函数内程序

def ir_distance_1_lt_10_event(msg):
    pass
ir_distance_sensor_ctrl.cond_wait('ir_distance_[port_id]_[compare_type]_[dist]')
描述:

等待红外深度传感器模块前方障碍物距离满足条件时,执行下一条指令

参数:
  • 'ir_distance_[port_id]_[compare_type]_[dist]' – 用于距离比较的字符串,含模块编号,比较类型和距离
  • port_id (int) – 红外深度传感器模块编号,范围为[1:4]
  • compare_type – 比较类型,可以为 eq, ge, gt, le, lt, 分别表示等于,大于等于,大于,小于等于,小于
  • dist – 用于比较的距离,精确度为 1 cm,范围为 5~500 cm,误差率为 5%
返回:

示例:

ir_distance_sensor_ctrl.cond_wait('ir_distance_1_gt_50')

示例说明:

等待 1 号红外深度传感器模块前方障碍物距离大于 50 cm 时,执行下一条指令

ir_distance_sensor_ctrl.check_condition('ir_distance_[port_id]_[compare_type]_[dist]')
描述:

判断红外深度传感器模块前方障碍物距离是否满足条件

参数:
  • 'ir_distance_[port_id]_[compare_type]_[dist]' – 用于距离比较的字符串,含模块编号,比较类型和距离
  • port_id (int) – 红外深度传感器模块编号,范围为[1:4]
  • compare_type – 比较类型,可以为 eq, ge, gt, le, lt, 分别表示等于,大于等于,大于,小于等于,小于
  • dist – 用于比较的距离,精确度为 1 cm,范围为 5~500 cm,误差率为 5%
返回:

是否满足条件,满足条件时返回真,否则返回假。

返回类型:

bool

示例:
1
2
3
4
#当检测到 1 号红外深度传感器前方障碍物距离小于 10 cm 时,运行函数内程序

if ir_distance_sensor_ctrl.check_condition('ir_distance_1_gt_50'):
    pass

提示

模块说明请参考 红外深度传感器

传感器转接模块

sensor_adapter_ctrl.get_sensor_adapter_adc(board_id, port_num)
描述:

获取传感器转接模块相应端口模拟引脚的 ADC 值

参数:
  • board_id (int) – 传感器转接模块编号,范围为[1:6]
  • port_num (uint8) – 传感器转接模块上的端口号,范围为[1:2]
  • wait_for_complete (bool) – 是否等待执行完成,默认为 True
返回:

传感器转接模块相应端口模拟引脚的 ADC 值,范围为[0:1023]

返回类型:

uint16

示例:

ret = sensor_adapter_ctrl.get_sensor_adapter_adc(1, 2)

示例说明:

获取 1 号传感器转接模块 2 号端口模拟引脚的 ADC 值

sensor_adapter_ctrl.get_sensor_adapter_pulse_period(board_id, port_num)
描述:

获取传感器转接模块相应端口引脚的脉冲持续时间

参数:
  • board_id (int) – 传感器转接模块编号,范围为[1:6]
  • port_num (uint8) – 传感器转接模块上的端口号,范围为[1:2]
返回:

传感器转接模块相应端口引脚的脉冲持续时间,精确度为 1 ms

返回类型:

uint32

示例:

ret = sensor_adapter_ctrl.get_sensor_pulse_period(1, 2)

示例说明:

获取 1 号传感器转接模块 2 号端口引脚脉冲持续时间

def sensor_adapter[board_id]_port[port_id]_[judge_type]_event(msg):
描述:

当检测到传感器转接模块相应端口引脚跳变为高电平/低电平/双向,运行函数内程序

参数:
  • board_id (int) – 传感器转接模块编号,范围为[1:6]
  • port_num (uint8) – 传感器转接模块上的端口号,范围为[1:2]
  • judge_type – 触发条件,可以为 high, low, trigger,分别表示高电平,低电平还是双向跳变
返回:

示例:
1
2
3
4
#当检测到 1 号传感器转接模块 2 号端口引脚跳变为高电平时,运行函数内程序

def sensor_adapter1_port2_high_event(msg):
    pass
sensor_adapter_ctrl.cond_wait(rm_define.cond_sensor_adapter[board_id]_port[port_id]_[judge_type]_event)
描述:

等待传感器转接模块相应端口引脚脉冲为(高/低/跳变)时,执行下一条指令

参数:
  • board_id (int) – 传感器转接模块编号,范围为[1:6]
  • port_num (uint8) – 传感器转接模块上的端口号,范围为[1:2]
  • judge_type – 触发条件,可以为 high, low, trigger,分别表示高电平,低电平还是双向跳变
返回:

示例:

sensor_adapter_ctrl.cond_wait(rm_define.cond_sensor_adapter1_port2_high_event)

示例说明:

等待 1 号传感器转接模块 2 号端口引脚为高电平时,执行下一条指令

sensor_adapter_ctrl.check_condition(rm_define.cond_sensor_adapter[board_id]_port[port_id]_[judge_type]_event)
描述:

判断传感器转接模块相应端口引脚脉冲是否为(高/低/跳变)

参数:
  • board_id (int) – 传感器转接模块编号,范围为[1:6]
  • port_num (uint8) – 传感器转接模块上的端口号,范围为[1:2]
  • judge_type – 触发条件,可以为 high, low, trigger,分别表示高电平,低电平还是双向跳变
返回:

是否满足条件,满足条件时返回真,否则返回假。

返回类型:

bool

示例:
1
2
3
4
#如果 1 号传感器转接模块 2 号端口引脚正在跳变时,执行下一条指令

if sensor_adapter_ctrl.check_condition(rm_define.cond_sensor_adapter1_port2_trigger_event):
    pass

提示

模块说明请参考 传感器转接模块

UART

serial_ctrl.serial_config(baud_rate, data_bit, odd_even, stop_bit)
描述:

设置串口的波特率、数据位、校验位以及停止位属性

参数:
  • baud_rate – 设置波特率,可选波特率为 9600、19200、38400、57600、115200
  • data_bit – 设置数据位,可选的数据位为 cs7、cs8
  • odd_even_crc – 设置奇偶校验,详细见表格 odd_even_crc
  • stop_bit – 设置停止位,可选的停止位为 1、2
返回:

示例:

serial_ctrl.serial_config(9600, 'cs8', 'none', 1)

示例说明:

设置串口的波特率为 9600,数据位 8 位,不使用奇偶校验,停止位为 1 位

serial_ctrl.write_line(msg_string)
描述:发送字符串信息,自动添加换行 '\n'
参数:msg_string (string) – 需要发送的字符串信息,发送时字符串后自动添加 '\n'
返回:
示例:serial_ctrl.write_line('RoboMaster EP')
示例说明:向串口写入 'RoboMaster EP\n' ,最后的换行自动添加,用户只需要发送 'RoboMaster EP'
serial_ctrl.write_string(msg_string)
描述:发送字符串信息
参数:msg_string (string) – 需要发送的字符串信息
返回:
示例:serial_ctrl.write_string('RoboMaster EP')
示例说明:向串口写入 'RoboMaster EP'
serial_ctrl.write_number(value)
描述:将数字参数转换成字符串,并通过串口发送出去
参数:value (int) – 需要发送的值
返回:
示例:serial_ctrl.write_number(12)
示例说明:向串口中写入字符串 '12'
serial_ctrl.write_numbers(value1, value2, value3...)
描述:

将数字列表转换成字符串,并通过串口发送出去

参数:
  • value1 (int) – 需要发送数字列表的值
  • value2 (int) – 需要发送数字列表的值
  • value3 (int) – 需要发送数字列表的值
返回:

示例:

serial_ctrl.write_numbers(12,13,14)

示例说明:

向串口中写入字符串 '12,13,14'

serial_ctrl.write_value(key, value)
描述:

将参数以键值对的形式组成字符串,并通过串口发送出去

参数:
  • key (string) – 需要发送的关键字
  • value (int) – 需要发送的值
返回:

示例:

serial_ctrl.write_value('x', 12)

示例说明:

向串口中写入字符串 'x:12'

serial_ctrl.read_line([timeout])
描述:从串口中读取以 '\n' 结尾的字符串
参数:timeout (float) – 可选,超时时间,单位为秒,默认为永久阻塞
返回:通过串口读取到的字符串
返回类型:string
示例:recv = serial_ctrl.read_line()
示例说明:从串口读取一行以 '\n' 结尾的字符串
serial_ctrl.read_string([timeout])
描述:从串口中读取字符串(字符串可以不以 '\n' 结尾)
参数:timeout (float) – 可选,超时时间,单位为秒,默认为永久阻塞
返回:通过串口读取到的字符串
返回类型:string
示例:recv = serial_ctrl.read_string()
示例说明:从串口读取一个字符串
serial_ctrl.read_until(stop_sig[, timeout])
描述:

从串口中读取字符串,直到匹配到指定的结束字符 'stop_sig'

参数:
  • stop_sig – 指定的结束字符,参数类型为字符,范围为[ '\n' | '$' | '#' | '.' | ':' | ';' ]
  • timeout (float) – 可选,超时时间,单位为秒,默认为永久阻塞
返回:

通过串口读取到的匹配字符串

返回类型:

string

示例:

serial_ctrl.read_until('#')

示例说明:

从串口中读取字符串,直到匹配到 '#' 停止读取

odd_even_crc
none 不使用奇偶校验
odd 使用奇校验
even 使用偶校验

提示

模块说明请参考 UART

编队控制

介绍

编队控制功能是通过明文 SDK 对连接在同一个局域网内的多个机器人进行动作编排,实现整体控制的功能。用户可以使用该功能进行更复杂的动作控制,实现编队舞蹈,很具有观赏性。

原理为多台机器人通过 WIFI 路由器模式在同一个局域网内建立连接后,用户在 PC 上通过 Python 脚本与多台机器人通信,同时向多台机器人下发明文 SDK 指令,从而实现编队控制的功能。在本章节中主要介绍一个用 Python 脚本通过明文 SDK 实现编队控制的简单示例。

示例环境

  • 硬件设备:路由器、两台 EP 机器人、 PC
  • Python版本:Python 3.6

建立多机连接

将 EP 机器人设置为 WIFI 路由器模式,使用 APP 将参与编队控制的 EP 依次接入同一个路由器中,连接成功后打开 APP 设置中的连接页面,记录 EP 的 IP 地址。具体步骤请参考 WIFI 路由器模式

运行示例程序

  1. 将IP地址依次填入参考代码中的 IP_LIST 列表中,并将脚本代码保存为 ep.py。

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    #!/usr/bin/env python3
    # coding=utf-8
    
    import sys
    import time
    import threading
    import socket
    
    IP_LIST = ['192.168.1.103', '192.168.1.117']
    EP_DICT = {}
    
    class EP:
            def __init__(self, ip):
                    self._IP = ip
                    self.__socket_ctrl = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
                    self.__socket_isRelease = True
                    self.__socket_isConnect = False
                    self.__thread_ctrl_recv = threading.Thread(target=self.__ctrl_recv)
                    self.__seq = 0
                    self.__ack_list = []
                    self.__ack_buf = 'ok'
    
            def __ctrl_recv(self):
                    while self.__socket_isConnect and not self.__socket_isRelease:
                            try:
                                    buf = self.__socket_ctrl.recv(1024).decode('utf-8')
                                    print('%s:%s' % (self._IP, buf))
                                    buf_list = buf.split(' ')
                                    if 'seq' in buf_list:
                                            self.__ack_list.append(int(buf_list[buf_list.index('seq') + 1]))
                                    self.__ack_buf = buf
                            except socket.error as msg:
                                    print('ctrl %s: %s' % (self._IP, msg))
    
            def start(self):
                    try:
                            self.__socket_ctrl.connect((self._IP, 40923))
                            self.__socket_isConnect = True
                            self.__socket_isRelease = False
                            self.__thread_ctrl_recv.start()
                            self.command('command')
                            self.command('robot mode free')
                    except socket.error as msg:
                            print('%s: %s' % (self._IP, msg))
    
            def exit(self):
                    if self.__socket_isConnect and not self.__socket_isRelease:
                            self.command('quit')
                    self.__socket_isRelease = True
                    try:
                            self.__socket_ctrl.shutdown(socket.SHUT_RDWR)
                            self.__socket_ctrl.close()
                            self.__thread_ctrl_recv.join()
                    except socket.error as msg:
                            print('%s: %s' % (self._IP, msg))
    
            def command(self, cmd):
                    self.__seq += 1
                    cmd = cmd + ' seq %d;' % self.__seq
                    print('%s:%s' % (self._IP, cmd))
                    self.__socket_ctrl.send(cmd.encode('utf-8'))
                    timeout = 2
                    while self.__seq not in self.__ack_list and timeout > 0:
                            time.sleep(0.01)
                            timeout -= 0.01
                    if self.__seq in self.__ack_list:
                            self.__ack_list.remove(self.__seq)
                    return self.__ack_buf
    
    if __name__ == "__main__":
            #实例化机器人
            for ip in IP_LIST:
                    print('%s connecting...' % ip)
                    EP_DICT[ip] = EP(ip)
                    EP_DICT[ip].start()
    
            for ip in IP_LIST:
                    EP_DICT[ip].command('gimbal moveto p 0 y 0 vp 90 vy 90 wait_for_complete false')
            time.sleep(3)
    
            while True:
                    for ip in IP_LIST:
                            EP_DICT[ip].command('gimbal moveto p 0 y 45 vp 90 vy 90 wait_for_complete false')
                    time.sleep(3)
                    for ip in IP_LIST:
                            EP_DICT[ip].command('gimbal moveto p 0 y -45 vp 90 vy 90 wait_for_complete false')
                    time.sleep(3)
            for ip in IP_LIST:
                    EP_DICT[ip].exit()
    
  2. 运行脚本

  • Windows系统:完成Python环境后可直接点击 ep.py 启动脚本。
  • Linux系统:在命令终端输入 python ep.py 启动脚本。
  1. 运行效果

编队控制的多台机器人云台步调一致的在 YAW 轴方向往复运动。

_images/form_control.gif
  1. 运行结果

命令行端口输出多台机器人与主机之间的明文通讯数据。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
192.168.1.103 connecting...
192.168.1.103:command seq 1
192.168.1.103:ok seq 1
192.168.1.103:robot mode free seq 2
192.168.1.103:ok seq 2
192.168.1.117 connecting...
192.168.1.117:command seq 1
192.168.1.117:ok seq 1
192.168.1.117:robot mode free seq 2
192.168.1.117:ok seq 2
192.168.1.103:gimbal moveto p 0 y 0 vp 90 vy 90 wait_for_complete false seq 3
192.168.1.103:ok seq 3
192.168.1.117:gimbal moveto p 0 y 0 vp 90 vy 90 wait_for_complete false seq 3
192.168.1.117:ok seq 3

版本说明

为了提供更好的使用体验以及配合更强大的功能,开发者文档将会定期进行版本更新。使用前请确认您的机器人版本,SDK版本以及文档版本是否匹配。若不匹配,建议您更新机器人至要求的版本,或者使用对应版本的文档。

版本信息参考下表:

文档版本 S1 版本 EP 版本 明文 SDK 版本
v0.2.0(latest) v00.06.01.00 v01.01.01.00 v00.00.00.52
v0.1.2 v00.05.01.00 v01.00.00.00 v00.00.00.32
v0.1.1
v0.1.0

Indices and tables