步进电机可用于微控制器项目的各个领域,例如制作机器人、机械臂、自动门锁系统等。本文将向您解释步进电机(单极和双极步进电机)的构造、基本原理、不同的控制类型(半步和全步)、接口技术(使用 L293D 或 ULN2003)以及使用 C 语言对微控制器进行编程以控制步进电机。步进电机类型市场上有两种基本类型的步进电机。
单极步进电机(Unipolar stepper motor)
单极步进电机有五或六根电线和四个线圈(实际上是两个线圈,每个线圈由中心连接分割为两部分)。线圈的中心连接连接在一起并用作电源连接。它们被称为单极步进电机,因为电源总是从一个极进入。


双极步进电机(Bipolar stepper motor)
双极步进电机通常有四根电线。与单极步进电机不同,双极步进电机没有公共中心连接。它们有两组独立的线圈。您可以通过测量电线之间的电阻来区分它们与单极步进电机。您应该找到两对具有相同电阻的电线。如果您将仪表的引线连接到两根未连接的电线(即未连接到同一线圈),您应该看到无穷大电阻(或无连续性)。


正如前面所说的,我们将主要讨论“单极步进电机”,这是市场上最常见的步进电机类型。下面给出了一个 6 引线步进电机的简单示例,在 5 引线步进电机中,第5 根和第 6 根线连接在一起形成 1 根公共线。

步进电机的工作原理
现在让我们讨论一下步进电机的工作原理。当我们给步进电机的线圈通电时,步进电机的轴(实际上是一个永磁体)会根据通电线圈的极点自行对齐。因此,当电机线圈以特定顺序通电时,电机轴会根据线圈的极点自行对齐,从而旋转。下面给出了通电操作的一个小例子。

您可以在示例中看到,当线圈“A”通电时,如上图所示,在“A+A\”处会产生南北极性,磁轴会根据产生的极性自动对齐。当下一个线圈通电时,轴会再次对齐并迈出一步。这就是工作原理。

我们已经看到,要使步进电机工作,我们需要按顺序给线圈通电。
步进序列
步进电机可以以两种不同的模式或序列驱动。即
- 全步进序列(Full Step Sequence)
- 半步进序列(Half Step Sequence)
我们将逐一介绍这些序列。
全步进序列
在全步进序列中,两个线圈同时通电,电机轴旋转。下表给出了线圈通电的顺序。
Full Mode Sequence | ||||
---|---|---|---|---|
Step | A | B | A\ | B\ |
0 | 1 | 1 | 0 | 0 |
1 | 0 | 1 | 1 | 0 |
2 | 0 | 0 | 1 | 1 |
3 | 1 | 0 | 0 | 1 |
下面的动画图给出了完整模式序列的工作原理。

半步进序列
在半模式步进序列中,电机步进角减小到全模式的一半。因此,角度分辨率也增加了,即,它变为全模式角度分辨率的两倍。此外,在半模式序列中,步数是全模式的两倍。半模式通常比全模式更受欢迎。下表显示了线圈通电的模式。
Half Mode Sequence | ||||
---|---|---|---|---|
Step | A | B | A\ | B\ |
0 | 1 | 1 | 0 | 0 |
1 | 0 | 1 | 0 | 0 |
2 | 0 | 1 | 1 | 0 |
3 | 0 | 0 | 1 | 0 |
4 | 0 | 0 | 1 | 1 |
5 | 0 | 0 | 0 | 1 |
6 | 1 | 0 | 0 | 1 |
7 | 1 | 0 | 0 | 0 |
下面的动画图给出了半模式序列的工作原理。

步进角
步进电机的步进角定义为电机每走一步所经过的角度。要计算步进角,只需用 360 除以电机完成一圈所需的步数。正如我们所见,在半模式下,电机完成一圈所需的步数加倍,因此步进角减小到一半。
如上例所示,步进电机在全模式下旋转需要 4 步才能完成一圈,因此步进角可以计算为…
步进角 ø = 360° / 4 = 90°
在半模式下,步进角减半,即 45°。
因此,我们可以通过这种方式计算任何步进电机的步进角。通常,步进角在您使用的步进电机的规格表中给出。了解步进电机的步进角有助于您校准电机的旋转,也有助于您将电机移动到正确的角度位置。
双极步进电机的步进顺序
双极电机的结构更简单。它有两个绕组,没有中心抽头,中心有一个永磁体,就像单极步进电机一样。由于结构更简单,步进顺序有点复杂,因为两个线圈的功率必须以这样一种方式控制,即两极的极性反转。下表显示了此极性顺序。
Polarity Sequence | ||||
---|---|---|---|---|
Step | A | A\ | B | B\ |
0 | +ve | -ve | -ve | -ve |
1 | -ve | -ve | +ve | -ve |
2 | -ve | +ve | -ve | -ve |
3 | -ve | -ve | -ve | +ve |
通过一次激活一个线圈,可以根据微控制器的逻辑电平来解释上述极性序列,如下表所示。
Step Sequence | ||||
---|---|---|---|---|
Step | A | A\ | B | B\ |
0 | 1 | 0 | 0 | 0 |
1 | 0 | 0 | 1 | 0 |
2 | 0 | 1 | 0 | 0 |
3 | 0 | 0 | 0 | 1 |
步进电机连接
连接单极步进电机
实际上,将步进电机连接到控制器的方法有很多,其中最常用的接口是:
使用 L293D – H 桥电机驱动器的接口
使用 ULN2003/2004 – 达林顿(Darlington)阵列的接口
我们将逐一讨论这两种连接技术。上述方法需要 4 个控制器引脚进行接口。
使用 L293D 连接单极步进机

正如您在上面的电路中看到的,四个引脚“控制器引脚 1”、2、3 和 4 将根据控制器中编程的步进顺序控制步进电机的运动和方向。
使用 ULN2003/2004 连接单极步进机

正如在 L293D 的情况下已经讨论过的,在这个电路中,四个引脚“控制器引脚 1”、2、3 和 4 也将根据控制器发送的步进顺序控制步进电机的运动和方向。
连接双极步进电机
正如我们所研究的,双极步进电机有 2 个不同的线圈。双极步进电机的步进顺序与单极步进电机相同。该电机的驱动电路需要一个 H 桥,因为它允许独立控制所施加电源的极性。这可以按照下图所示完成:

步进电机编程
单极电机全步序列编程
#include <reg51.H>
#define stepper P2
void delay()
{
unsigned char i,j,k;
for(i=0;i<6;i++) {
for(j=0;j<255;j++)
for(k=0;k<255;k++);
}
}
void main()
{
while (1) {
stepper = 0x0C;
delay();
stepper = 0x06;
delay();
stepper = 0x03;
delay();
stepper = 0x09;
delay();
}
}
Proteus演示结果(以ULN2003芯片为例),电机步进角设为90°。

单极电机半步序列编程
#include <reg51.h>
#include <stdio.h>
#define stepper P2
void delay()
{
unsigned char i,j,k;
for(i=0;i<6;i++) {
for(j=0;j<255;j++)
for(k=0;k<255;k++);
}
}
void main()
{
while (1) {
stepper = 0x08;
delay();
stepper = 0x0C;
delay();
stepper = 0x04;
delay();
stepper = 0x06;
delay();
stepper = 0x02;
delay();
stepper = 0x03;
delay();
stepper = 0x01;
delay();
stepper = 0x09;
delay();
}
}
Proteus演示结果

双极步进电机编程
#include <reg51.h>
#include <stdio.h>
#define stepper P2
void delay()
{
unsigned char i,j,k;
for(i=0;i<6;i++) {
for(j=0;j<255;j++)
for(k=0;k<255;k++);
}
}
void main()
{
while (1) {
stepper = 0x08;
delay();
stepper = 0x02;
delay();
stepper = 0x04;
delay();
stepper = 0x01;
delay();
}
}
Proteus演示结果(以L293D芯片为例),电机步进角设为90°。

将电机的步进角改为1.8°,以下代码可实现步进电机正反转180°。
#include <reg51.h>
// Define motor control port
#define stepper P2 // Connect motor driver inputs to Port 2
// Delay function (1ms delay approximation for a 12 MHz crystal)
void delay(unsigned int time) {
unsigned int i, j;
for (i = 0; i < time; i++) {
for (j = 0; j < 250; j++); // Adjusted for 12 MHz clock
}
}
// Function to rotate the stepper motor in full-step mode
void stepper_full_step(int steps, int direction) {
int i, step;
for (step = 0; step < steps; step++) {
if (direction == 0) { // Forward rotation
stepper = 0x08; // IN1 and IN4 ON (binary: 1001)
delay(30);
stepper = 0x02; // IN1 and IN2 ON (binary: 0011)
delay(30);
stepper = 0x04; // IN2 and IN3 ON (binary: 0110)
delay(30);
stepper = 0x01; // IN3 and IN4 ON (binary: 1100)
delay(30);
} else { // Reverse rotation
stepper = 0x01; // IN3 and IN4 ON (binary: 1100)
delay(30);
stepper = 0x04; // IN2 and IN3 ON (binary: 0110)
delay(30);
stepper = 0x02; // IN1 and IN2 ON (binary: 0011)
delay(30);
stepper = 0x08; // IN1 and IN4 ON (binary: 1001)
delay(30);
}
}
}
void main() {
while (1) {
stepper_full_step(25, 0); // Rotate 180° forward
delay(1000); // 1-second delay
stepper_full_step(25, 1); // Rotate 180° backward
delay(1000); // 1-second delay
}
}