一、前言

当我们在电脑上输入一个目标速度,例如让电机以 100 rpm 的速度旋转时,电机是如何理解这个数字,并最终产生运动的?

计算机发送的是数字,电机执行的却是物理运动。两者之间,需要经历通信协议、驱动器控制程序、功率电路以及传感器反馈等多个环节。

以常见的伺服电机和 CANopen 通信协议为例,我们可以把整个过程理解为:

正在绘制图表…

这条链路包含三个不同的层次:

层次核心问题关键技术
通信层数据怎么传到电机?CAN、CANopen、SDO、PDO
控制层数字指令如何变成目标速度和转矩?对象字典、单位换算、CiA 402、PID、FOC
物理层电机为什么真的会转?PWM、功率开关、绕组电流、电磁转矩

理解时不要把这三个层次混在一起。CANopen 负责传输和定义参数,电机控制算法负责决定如何驱动,功率电路才负责向电机提供实际能量。

下面从实际指令出发,逐步理解这个过程。

第一步:上位机如何告诉电机该做什么?

在机器人系统中,上位机可以是电脑、控制板或机器人主控制器。它负责向电机驱动器发送控制指令。

例如,我们希望电机以指定速度运行,就需要告诉驱动器:

  • 当前应该处于什么控制状态?
  • 使用什么控制模式?
  • 目标速度是多少?

CANopen 是一种建立在 CAN 总线之上的高层通信协议。它不仅规定了数据如何传输,还定义了一套常见的参数组织方式,称为对象字典(Object Dictionary)。

对象字典可以理解为驱动器内部的一张参数表。不同的索引对应不同的控制参数或状态信息。

以常见的 CiA 402 驱动器配置为例:

索引名称作用
0x6040Controlword控制驱动器状态,例如使能
0x6041Statusword读取驱动器当前状态
0x6060Modes of operation设置控制模式
0x6061Modes of operation display读取当前生效的控制模式
0x60FFTarget velocity设置目标速度
0x606CVelocity actual value读取实际速度

这些索引属于常见的 CiA 402 对象定义,但驱动器是否支持它们,以及参数的单位、缩放方式,都需要以具体设备手册为准。

第二步:理解几个关键控制指令

1. 0x6040:控制字

控制字用于控制驱动器状态,例如请求驱动器使能。

常见的 CiA 402 控制状态转换操作包括:

  • 0x0006:Shutdown,请求进入准备使能状态。
  • 0x0007:Switch on,请求进入已接通状态。
  • 0x000F:Enable operation,请求使能运行。
  • 0x0080:Fault reset,故障复位请求,具体行为取决于设备状态和驱动器实现。

这些值是不可以随意排列的启动口令。驱动器有自己的状态机,通常需要按照规定的状态转换顺序操作,并确认状态字中的反馈。

例如,即使发送了 0x000F,如果驱动器仍处于故障状态、电源未就绪或存在安全互锁,电机也不一定能够运行。

2. 0x6060:工作模式

电机驱动器可以工作在不同模式下,例如位置控制、速度控制和转矩控制。

常见的 CiA 402 模式值包括:

模式值模式含义
1Profile Position按目标位置运动
3Profile Velocity按目标速度运动
6Homing执行回零操作
8CSP周期同步位置模式
9CSV周期同步速度模式
10CST周期同步转矩模式
  • 并不是所有驱动器都支持全部模式

如果想让电机以指定速度运行,就需要选择驱动器支持的速度控制模式,并确认该模式对应的目标参数和控制流程。

3. 0x60FF:目标速度

假设我们希望电机达到目标速度,就可以使用 0x60FF 这个常见的目标速度对象。

需要注意:写入的数值不一定直接等于 rpm。

例如,写入数字 1000,它究竟代表 1000 rpm、100 rpm,还是经过特定比例缩放的内部数值,取决于驱动器的单位定义、电子齿轮比和参数配置。

因此,实际使用时必须先查阅驱动器手册,确认数据类型和缩放比例。

第三步:数字指令如何通过 CAN 总线传输?

CAN 总线传输的不是文字,而是由标识符和数据字节组成的报文。

在 CANopen 中,SDO(服务数据对象)常用于读写对象字典参数。

例如,假设:

  • 驱动器节点 ID 为 1;
  • 使用标准 CANopen SDO;
  • 要向 0x60FF:00 写入一个 32 位整数;
  • 写入的原始数值为 1000。

对应的经典 CANopen SDO 下载请求可以表示为:

字段数值含义
CAN ID0x601节点 1 的 SDO 请求
Byte 00x23发起 4 字节数据写入
Byte 10xFF索引低字节
Byte 20x60索引高字节
Byte 30x00子索引
Byte 40xE8数值 1000 的低字节
Byte 50x03数值 1000 的次低字节
Byte 60x00数值的次高字节
Byte 70x00数值的高字节

CANopen SDO 数据部分:小端,低字节先发

  • 第 1 字节 (最低):0xE8
  • 第 2 字节:0x03
  • 第 3 字节:0x00
  • 第 4 字节 (最高):0x00

整帧数据为:

TEXT
CAN ID: 0x601
Data:   23 FF 60 00 E8 03 00 00

这里的 1000 按照小端序编码为 E8 03 00 00。

如果写入成功,驱动器通常会返回 SDO 响应:

TEXT
CAN ID: 0x581
Data:   60 FF 60 00 00 00 00 00

其中 0x581 是节点 1 的常见 SDO 响应标识符,0x60 表示写入成功的确认响应。

但要特别注意:这条报文只是一个参数写入示例,不代表发送后电机就一定会转动。 实际控制还需要正确的工作模式、驱动器状态、参数单位和设备配置。

第四步:驱动器收到指令后做了什么?

CAN 总线只是负责传输数据。真正决定电机如何运动的是驱动器内部的控制程序。

当驱动器收到一条指令后,通常需要完成以下工作:

  1. 接收并校验 CAN 报文。
  2. 根据 CANopen 协议解析请求。
  3. 定位对象字典中的目标参数。
  4. 检查数据类型、参数范围和当前驱动器状态。
  5. 将目标值交给相应的控制算法。

例如,当目标速度被写入后,驱动器会将其作为控制目标。

如果工作在速度控制模式,控制程序就需要比较目标速度和当前实际速度,并根据两者之间的误差计算控制输出。

这一过程可以简化为:

TEXT
目标速度
   ↓
与实际速度比较
   ↓
计算速度误差
   ↓
速度控制器(例如 PI)
   ↓
生成转矩或电流指令
   ↓
电流控制器
   ↓
控制功率器件

具体控制结构因电机类型和驱动器设计而异,但速度环、电流环是许多伺服系统中常见的控制结构。

第五步:电信号如何让电机真正转动?

驱动器最终需要控制电机绕组中的电流,才能产生电磁转矩。

以常见的永磁同步电机为例,电机内部主要包含定子和转子:

  • 定子:具有绕组,通入受控电流后产生磁场。
  • 转子:具有永磁体或其他磁场结构。
  • 功率驱动电路:通过控制功率器件的开关,将直流电源转换成电机所需的多相电压和电流。

在常见的伺服驱动器中,控制器会使用 PWM 等方式控制功率器件;对于采用磁场定向控制(FOC)的永磁同步电机,还会对电流进行坐标变换和调节,以控制转矩与磁场分量。

当绕组电流受到控制后,定子磁场与转子磁场之间产生电磁作用,电机就会输出转矩。

只要转矩足以克服摩擦、负载和其他阻力,转子便开始转动。

因此,从数字指令到机械运动,中间并不是简单的“数字直接变成转速”,而是经过了控制算法、电流调节和电磁能量转换。

第六步:编码器如何知道电机转了多少?

如果只给电机供电,它可能会旋转,但控制器未必知道它实际转了多少、速度是多少。

为了实现精准控制,伺服电机通常会配备编码器等传感器。

编码器可以提供转子位置或增量计数信息。驱动器根据一段时间内的位置变化,估算实际转速。

例如,假设:

  • 在 0.1 秒内,编码器计数增加了 1000;
  • 经过设备定义的解码方式换算后,每转对应 4000 个计数;
  • 暂时忽略滤波、量化和测量误差。

则转速估算为:

n=ΔNC×60Δtn=\frac{\Delta N}{C}\times\frac{60}{\Delta t}其中:

  • ΔN\Delta N:这段时间内的计数变化;
  • CC:每转对应的有效计数;
  • Δt\Delta t:测量时间,单位为秒;
  • nn:转速,单位为 rpm。

代入示例:

n=10004000×600.1=150 rpmn=\frac{1000}{4000}\times\frac{60}{0.1} =150\ \text{rpm}这说明电机在该测量区间内的平均转速约为 150 rpm。

实际计算时,必须确认编码器计数定义、减速器传动比以及驱动器是否已经完成单位换算。

第七步:闭环控制如何让电机稳定运行?

假设目标速度为 100 rpm,而编码器测得的实际速度只有 80 rpm。

控制器就会计算速度误差:

e=100−80=20 rpme=100-80=20\ \text{rpm}

速度控制器根据误差和内部参数,调整转矩或电流指令,让电机输出更合适的转矩。

随后,驱动器再次读取实际速度,重新计算误差并调整输出。

这一过程会不断重复:

TEXT
目标速度:100 rpm
       ↓
比较目标与实际速度
       ↓
实际速度:80 rpm
       ↓
计算误差:20 rpm
       ↓
调整电流 / 转矩指令
       ↓
电机速度发生变化
       ↓
编码器再次反馈实际速度
       └───────循环

这就是闭环控制的基本思想:不是发出一次指令就不再管它,而是持续测量实际结果,并根据误差修正控制输出。

当负载突然增大时,电机转速可能下降。闭环控制可以检测这种变化,并尝试通过调整输出转矩维持目标速度,但它能否维持速度,仍取决于电机功率、驱动器能力和负载大小。

思考

学习电机控制时,很容易把注意力集中在通信指令上,例如 0x6040、0x6060 和 0x60FF。但这些指令只是整个系统中的一部分。

0x6040 负责请求驱动器改变状态,0x6060 用于选择控制模式,0x60FF 可以设置目标速度。它们本身不会直接产生电磁转矩。真正让电机运动的,是驱动器把数字目标转换成控制量,再通过功率电路控制绕组电流;而编码器反馈与闭环算法,让电机能够根据实际运动状态持续调整输出。

理解这一点之后,机器人控制就不再只是发送几个十六进制数字,而是一个连接了通信协议、嵌入式软件、控制理论、电力电子和机械运动的完整系统。

这也是我认为学习机器人硬件最重要的一点:不要只记住某条指令的含义,更要弄清楚这条指令进入系统之后,究竟改变了什么,以及它最终如何影响真实世界。