单片机
返回首页

stm32单片机控制28BYJ48步进电机原理及代码

2025-08-26 来源:cnblogs

 命名方式(以28BYJ48步进电机为例)

28BYJ48步进电机的编号

28-----步进电机的有效最大外径是28毫米

B-----表示步进电机

Y-----表示永磁式

J-----表示减速型

48-----表示四相八拍

工作原理

1、五线四相步进电机,不同相位得电会让步进电机的转子转动一个角度,按一定规律给不同的相位通电,就可以让步进电机连续转动,下表就是通电的顺序。

表里面的顺,逆时针的方向只是代表相位给电时序,



注:总共五条线,一个是VCC,剩下四条分别接上ABCD相

分别对应与ULN2003/ULN2003A驱动芯片的5V以及4个输入口对应连接

2、每走一个位置,都要给一定的延时,不然还没等转子到位,下一个脉冲就进来了,肯定会引起错误,导致电机堵转或者异常震动。

3、通过改变延时的时间,就可以控制电机的转速,不能太慢,也不要太快,不断调试到合理范围就行。

4、单片机IO口和电机四条相线连接时,一定不能错误,要按照顺序相连接。

5、调换得电的顺序,就可以控制电机的转向。

注意在51单片机中,为IO口置0相当于是高电平,而置1的时候相当于是低电平,和上面的图片一致(GND)

二、关键实验程序

在编写注释的时候用的是ANSI编码器,在这里部分注释可能会出现乱码,复制到编译器中就会正常显示(也注意一般用UTF-8编码器进行编写,ANSI编码器对中文不友好,一般一个汉字用的2个字符储存,所以在转存的时候就会出现乱码)


#ifndef __BSP_ULN2003_H__

#define __BSP_ULN2003_H__


#include

#include 'bsp_SysTick.h'


#define STEPPER_ANGLE 0.703125   //  360/(4096/4)=360/512=0.703125


enum dir{Pos, Neg};   //Pos = 0, Neg = 1  //enumΪ¶¨ÒåΪö¾Ù


#define IN1_HIGH GPIO_WriteBit(GPIOA, GPIO_Pin_4, Bit_SET)

#define IN1_LOW GPIO_WriteBit(GPIOA, GPIO_Pin_4, Bit_RESET)


#define IN2_HIGH GPIO_WriteBit(GPIOA, GPIO_Pin_5, Bit_SET)

#define IN2_LOW GPIO_WriteBit(GPIOA, GPIO_Pin_5, Bit_RESET)


#define IN3_HIGH GPIO_WriteBit(GPIOA, GPIO_Pin_6, Bit_SET)

#define IN3_LOW GPIO_WriteBit(GPIOA, GPIO_Pin_6, Bit_RESET)


#define IN4_HIGH GPIO_WriteBit(GPIOA, GPIO_Pin_7, Bit_SET)

#define IN4_LOW GPIO_WriteBit(GPIOA, GPIO_Pin_7, Bit_RESET)


void ULN2003_Configuration(void);

void stepper(unsigned int dir, unsigned int speed);

void angle_control(unsigned int dir, double angle, unsigned int speed);


#endif

调用函数


/*

Á¬Ïß±í£º

STM32 ULN2003Çý¶¯

PA4      <-------> IN1

PA5 <-------> IN2

PA6 <-------> IN3

PA7 <-------> IN4

5V 28BYJ-48²½½øµç»ú£¬ÄÚ²¿´øÓмõËÙ×°Öà ¼õËٱȣº1/64   ²½¾à½Ç£º5.625¡ã/64£¨64¸öÂö³åת¶¯5.625¡ã£©


ÕýÏòת¶¯£º

ËÄÏà°ËÅÄ¿ØÖÆË³Ðò£º(A-AB-B-BC-C-CD-D-DA)

1 2 3 4 5 6 7 8

A - - + + + + + -

B + - - - + + + +

C + + + - - - + +

D + + + + + - - -

·´Ïòת¶¯£º(DA-D-CD-C-BC-B-AB-A)

*/


#include 'bsp_uln2003.h'


void ULN2003_Configuration(void)

{

GPIO_InitTypeDef GPIO_InitStructure;


RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7;

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;

GPIO_Init(GPIOA, &GPIO_InitStructure);

GPIO_WriteBit(GPIOA, GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7, Bit_RESET);

}


//ËÙ¶È¿ØÖÆ:

/*

dir: ˳£¬ÄæÊ±ÕëÐýת·½Ïò

speed£º×ªËÙ£¬·¶Î§[1,100]

*/

void stepper(unsigned int dir, unsigned int speed)

{

if(dir == Pos)

{

//step1:

IN1_HIGH;

IN2_LOW;

IN3_LOW;

IN4_LOW;

Delay_us(speed);

//step2:

IN1_HIGH;

IN2_HIGH;

IN3_LOW;

IN4_LOW;

Delay_us(speed);


//step3:

IN1_LOW;

IN2_HIGH;

IN3_LOW;

IN4_LOW;

Delay_us(speed);


//step4:

IN1_LOW;

IN2_HIGH;

IN3_HIGH;

IN4_LOW;

Delay_us(speed);


//step5:

IN1_LOW;

IN2_LOW;

IN3_HIGH;

IN4_LOW;

Delay_us(speed);


//step6:

IN1_LOW;

IN2_LOW;

IN3_HIGH;

IN4_HIGH;

Delay_us(speed);


//step7:

IN1_LOW;

IN2_LOW;

IN3_LOW;

IN4_HIGH;

Delay_us(speed);


//step8:

IN1_HIGH;

IN2_LOW;

IN3_LOW;

IN4_HIGH;

Delay_us(speed);

}

else

{

//step1:

IN1_HIGH;

IN2_LOW;

IN3_LOW;

IN4_HIGH;

Delay_us(speed);


//step2:

IN1_LOW;

IN2_LOW;

IN3_LOW;

IN4_HIGH;

Delay_us(speed);


//step3:

IN1_LOW;

IN2_LOW;

IN3_HIGH;

IN4_HIGH;

Delay_us(speed);


//step4:

IN1_LOW;

IN2_LOW;

IN3_HIGH;

IN4_LOW;

Delay_us(speed);


//step5:

IN1_LOW;

IN2_HIGH;

IN3_HIGH;

IN4_LOW;

Delay_us(speed);


//step6:

IN1_LOW;

IN2_HIGH;

IN3_LOW;

IN4_LOW;

Delay_us(speed);


//step7:

IN1_HIGH;

IN2_HIGH;

IN3_LOW;

IN4_LOW;

Delay_us(speed);


//step8:

IN1_HIGH;

IN2_LOW;

IN3_LOW;

IN4_LOW;

Delay_us(speed);

}

}


//½Ç¶È¿ØÖÆ£º

/*

dir: ˳£¬ÄæÊ±ÕëÐýת·½Ïò

angle£º½Ç¶È£¬·¶Î§[0,360]

speed£º×ªËÙ£¬·¶Î§[1,100]

*/


void angle_control(unsigned int dir, double angle, unsigned int speed)

{

int i;

for(i = 0; i < angle / STEPPER_ANGLE; i++) //µ÷ÓÃ(angle / STEPPER_ANGLE)¸ö°ËÅÄ

stepper(dir, speed);

}


1、步进电机的减速比为1/64,即转子转动64圈,外面的转轴才会转动1圈

2、步进电机的步距角为5.624/64 (步进电机的定子绕组每次改变一次通电状态,步进电机外面的转轴转过的角度称步距角;即步进电机的最小旋转角度)

3、所以360/(5.624/64)≈ 4096 (步进电机外面的转轴转过一圈所需要改变定子绕组的通电状态次数)


这里补充介绍一个概念:步进角

步进电机的定子绕组每次改变一次通电状态,转子转过的角度称步进角。

(可以认为是电机内部的转子的最小旋转角度)

步进角 = (360)/m * Z * C

m-----定子相数

Z-----转子磁极对数

C-----通电方式

{ C = 1 ,单相轮流通电,双相轮流通电方式

  C = 2 , 双相轮流通电方式

1,相数:是指产生不同对极N,S磁场的激磁线圈对数

2,拍数:完成一个周期性变化所需脉冲数,以四相电机为例,有单相四拍的运行方式:(A-B-C-D),有双相四拍的运行方式:(AB-BC-CD-DA),有四相八拍的运行方式:(A-AB-B-BC-C-CD-D-DA)


这里的源码用的是双相轮流通电方式,在源码中可以看到四个相位MA,MB,MC,MD使能为高电平状态的相位数为相邻2个或1个(A-AB-B-BC-C-CD-D-DA)

步进电机的相关参数:


注意事项:由于电机的制造误差,安装误差,单片机的误差还有软件延时函数误差,这些误差累加起来之后,就会导致电机的转速、转动角度出现一定的误差。


进入单片机查看更多内容>>
相关视频
  • 【TI MSPM0 应用实战】智能小车+工业角度编码器+血氧仪+烟雾探测器!硬核参考设计详解!

  • 2022 Digi-Key KOL 系列: 你见过1GHz主频的单片机吗?Teensy 4.1开发板介绍

  • TI 新一代 C2000™ 微控制器:全方位助力伺服及马达驱动应用

  • MSP430电容触摸技术 - 防水Demo演示

  • 直播回放: Microchip Timberwolf™ 音频处理器在线研讨会

  • 基于灵动MM32W0系列MCU的指夹血氧仪控制及OTA升级应用方案分享

精选电路图
  • 1瓦线性调频增强器

  • 12V 转 28V DC-DC 变换器(基于 LM2585)

  • 红外遥控音量控制

  • LM317过压保护

  • 12V转110V/220V 500W逆变器

  • DS1669数字电位器

    相关电子头条文章