一、前言
本項(xiàng)目基于STC89C52單片機(jī),通過控制28BYJ-48步進(jìn)電機(jī)實(shí)現(xiàn)按角度正反轉(zhuǎn)旋轉(zhuǎn)的功能。28BYJ-48步進(jìn)電機(jī)是一種常用的電機(jī),精準(zhǔn)定位和高扭矩輸出,適用于許多小型的自動(dòng)化系統(tǒng)和機(jī)械裝置。
在這個(gè)項(xiàng)目中,使用STC89C52單片機(jī)作為控制器,這是一款強(qiáng)大而常用的8位單片機(jī)芯片,具有豐富的外設(shè)和強(qiáng)大的計(jì)算能力。通過編寫適當(dāng)?shù)某绦?,可以通過單片機(jī)的IO口來控制步進(jìn)電機(jī)的運(yùn)動(dòng)。
28BYJ-48步進(jìn)電機(jī)是一種低成本、低功耗的步進(jìn)電機(jī),擁有精確的定位能力和較高的轉(zhuǎn)矩輸出。將使用單片機(jī)與步進(jìn)電機(jī)之間的接口信號來驅(qū)動(dòng)電機(jī)旋轉(zhuǎn),并通過控制電流脈沖的頻率和順序來控制電機(jī)前進(jìn)或后退以及旋轉(zhuǎn)的角度。
本項(xiàng)目的目標(biāo)是實(shí)現(xiàn)根據(jù)用戶輸入的角度值,控制28BYJ-48步進(jìn)電機(jī)按指定角度進(jìn)行正反轉(zhuǎn)旋轉(zhuǎn)。通過靈活調(diào)整步進(jìn)電機(jī)的控制信號,可以實(shí)現(xiàn)不同角度范圍內(nèi)的精確旋轉(zhuǎn)。
在接下來的內(nèi)容將介紹所需的硬件和軟件資源,包括STC89C52單片機(jī)的基本特性、28BYJ-48步進(jìn)電機(jī)的工作原理,以及編寫控制程序的關(guān)鍵步驟。
二、設(shè)計(jì)流程
【1】硬件準(zhǔn)備:
- 51單片機(jī)開發(fā)板:選擇STC89C52單片機(jī)開發(fā)板。
- 28BYJ-48步進(jìn)電機(jī):一個(gè)28BYJ-48步進(jìn)電機(jī)+ULN2003驅(qū)動(dòng)板。
- 驅(qū)動(dòng)電路:使用ULN2003芯片來驅(qū)動(dòng)步進(jìn)電機(jī)。
- 連接線和電源:準(zhǔn)備連接線和電源供電。
【2】連接電路:
- 將51單片機(jī)與驅(qū)動(dòng)電路和步進(jìn)電機(jī)連接起來。
【3】編寫程序:
- 使用keil集成開發(fā)環(huán)境(IDE)編寫51單片機(jī)的控制程序。
- 初始化引腳和端口設(shè)置,配置控制步進(jìn)電機(jī)所需的引腳。
- 編寫函數(shù)來控制步進(jìn)電機(jī)的正反轉(zhuǎn)旋轉(zhuǎn)。
- 編寫函數(shù)來控制步進(jìn)電機(jī)按照指定的角度進(jìn)行旋轉(zhuǎn)。
【4】控制步進(jìn)電機(jī)旋轉(zhuǎn):
- 在主程序中,調(diào)用適當(dāng)?shù)暮瘮?shù)來控制步進(jìn)電機(jī)的旋轉(zhuǎn)。
- 使用按鍵輸入設(shè)備來觸發(fā)步進(jìn)電機(jī)的旋轉(zhuǎn)。
- 控制旋轉(zhuǎn)的角度、速度和方向。
【5】調(diào)試和測試:
- 通過編譯程序,并將生成的可執(zhí)行文件下載到51單片機(jī)開發(fā)板中。
三、代碼實(shí)現(xiàn)
3.1 電機(jī)正反轉(zhuǎn)控制
下面是通過STC89C52單片機(jī)控制28BYJ-48步進(jìn)電機(jī)實(shí)現(xiàn)正轉(zhuǎn)和反轉(zhuǎn)的實(shí)現(xiàn)代碼:
#include <reg52.h>
#include <intrins.h>
#define motorPort P1 // 步進(jìn)電機(jī)的控制引腳連接到P1口
#define clockwise 0 // 順時(shí)針方向
#define counterclockwise 1 // 逆時(shí)針方向
// 函數(shù)聲明
void delay(unsigned int time);
void motorRotate(unsigned char direction, unsigned int steps);
void main()
{
while (1)
{
// 正轉(zhuǎn),執(zhí)行一定的步數(shù) (這里為512步,可根據(jù)需要修改)
motorRotate(clockwise, 512);
delay(1000); // 延時(shí)1秒
// 反轉(zhuǎn),執(zhí)行一定的步數(shù)
motorRotate(counterclockwise, 256);
delay(1000); // 延時(shí)1秒
}
}
// 延時(shí)函數(shù)
void delay(unsigned int time)
{
unsigned int i, j;
for (i = time; i > 0; i--)
{
for (j = 110; j > 0; j--); // 指令周期延時(shí)
}
}
// 控制步進(jìn)電機(jī)旋轉(zhuǎn)
void motorRotate(unsigned char direction, unsigned int steps)
{
unsigned int i;
unsigned char motorSequence[8] = {0x01, 0x03, 0x02, 0x06, 0x04, 0x0C, 0x08, 0x09}; // 步進(jìn)電機(jī)的控制序列
for (i = 0; i < steps; i++)
{
if (direction == clockwise)
{
motorPort = motorSequence[i % 8];
}
else if (direction == counterclockwise)
{
motorPort = motorSequence[7 - (i % 8)];
}
delay(2); // 每步之間的延時(shí),可根據(jù)需要調(diào)整
}
motorPort = 0x00; // 停止電機(jī)
}
代碼里使用 STC89C52 單片機(jī)的 P1 口連接到28BYJ-48步進(jìn)電機(jī)的控制引腳。在 main
函數(shù)中,通過循環(huán)實(shí)現(xiàn)了正轉(zhuǎn)和反轉(zhuǎn)的功能。motorRotate
函數(shù)用于控制步進(jìn)電機(jī)的旋轉(zhuǎn)方向和步數(shù),其中 clockwise
和 counterclockwise
分別代表順時(shí)針和逆時(shí)針方向。
3.2 角度旋轉(zhuǎn)
下面代碼使用STC89C52單片機(jī)控制28BYJ-48步進(jìn)電機(jī)按指定的角度進(jìn)行正轉(zhuǎn)和反轉(zhuǎn),封裝子函數(shù)進(jìn)行調(diào)用。
#include <reg52.h>
// 定義28BYJ-48步進(jìn)電機(jī)的相序
unsigned char stepSequence[8] = {0x01, 0x03, 0x02, 0x06, 0x04, 0x0C, 0x08, 0x09};
// 定義步進(jìn)電機(jī)當(dāng)前位置和角度
unsigned char currentPosition = 0;
unsigned int currentAngle = 0;
// 延時(shí)函數(shù)
void delay(unsigned int time) {
unsigned int i, j;
for (i = 0; i < time; i++) {
for (j = 0; j < 120; j++);
}
}
// 步進(jìn)電機(jī)正轉(zhuǎn)函數(shù)
void stepForward(unsigned int angle) {
unsigned int steps = angle / 5; // 每步轉(zhuǎn)動(dòng)角度為5度
unsigned int i;
for (i = 0; i < steps; i++) {
currentPosition++;
if (currentPosition >= 8) {
currentPosition = 0;
}
P1 = stepSequence[currentPosition];
delay(10); // 控制步進(jìn)電機(jī)轉(zhuǎn)速,可調(diào)整延時(shí)時(shí)間
}
currentAngle += angle;
}
// 步進(jìn)電機(jī)反轉(zhuǎn)函數(shù)
void stepBackward(unsigned int angle) {
unsigned int steps = angle / 5; // 每步轉(zhuǎn)動(dòng)角度為5度
unsigned int i;
for (i = 0; i < steps; i++) {
if (currentPosition == 0) {
currentPosition = 8;
}
currentPosition--;
P1 = stepSequence[currentPosition];
delay(10); // 控制步進(jìn)電機(jī)轉(zhuǎn)速,可調(diào)整延時(shí)時(shí)間
}
currentAngle -= angle;
}
// 主函數(shù)
void main() {
while (1) {
// 正轉(zhuǎn)180度
stepForward(180);
delay(1000); // 停頓1秒鐘
// 反轉(zhuǎn)90度
stepBackward(90);
delay(1000); // 停頓1秒鐘
}
}
代碼使用STC89C52單片機(jī)的P1口作為輸出口,通過控制P1口輸出的電平來控制步進(jìn)電機(jī)的旋轉(zhuǎn)。步進(jìn)電機(jī)的相序存儲在stepSequence
數(shù)組中,每個(gè)元素對應(yīng)一個(gè)相位。stepForward
函數(shù)用于實(shí)現(xiàn)步進(jìn)電機(jī)的正轉(zhuǎn),stepBackward
函數(shù)用于實(shí)現(xiàn)步進(jìn)電機(jī)的反轉(zhuǎn)。delay
函數(shù)用于控制步進(jìn)電機(jī)的轉(zhuǎn)速,可以根據(jù)需要調(diào)整延時(shí)時(shí)間。
在主函數(shù)中,演示了步進(jìn)電機(jī)的正轉(zhuǎn)180度和反轉(zhuǎn)90度的操作。
3.3 按鍵控制電機(jī)
有2個(gè)按鍵,接在P2口3上面的,按下是低電平。下面代碼加入2個(gè)按鍵,實(shí)現(xiàn)了2個(gè)按鍵的功能。
#include <reg52.h>
#define motorPort P1 // 步進(jìn)電機(jī)的控制引腳連接到P1口
#define clockwise 0 // 順時(shí)針方向
#define counterclockwise 1 // 逆時(shí)針方向
sbit startBtn = P2^0; // 啟動(dòng)按鈕連接到P2.0口
sbit stopBtn = P2^1; // 停止按鈕連接到P2.1口
sbit cwBtn = P2^2; // 順時(shí)針按鈕連接到P2.2口
sbit ccwBtn = P2^3; // 逆時(shí)針按鈕連接到P2.3口
unsigned char motorSequence[8] = {0x01, 0x03, 0x02, 0x06, 0x04, 0x0C, 0x08, 0x09}; // 步進(jìn)電機(jī)的控制序列
bit motorRunning = 0; // 步進(jìn)電機(jī)是否正在運(yùn)行
unsigned int targetAngle = 0; // 目標(biāo)轉(zhuǎn)動(dòng)角度,初始為0
bit clockwiseDirection = 1; // 電機(jī)默認(rèn)啟動(dòng)方向?yàn)轫槙r(shí)針
// 函數(shù)聲明
void delay(unsigned int time);
void motorRotate(unsigned char direction, unsigned int steps);
void main()
{
while (1)
{
if (startBtn == 0) // 如果按下了啟動(dòng)按鈕
{
while (startBtn == 0); // 等待按鈕釋放
if (!motorRunning)
{
motorRunning = 1;
motorRotate(clockwiseDirection, targetAngle); // 啟動(dòng)電機(jī)
}
}
if (stopBtn == 0) // 如果按下了停止按鈕
{
while (stopBtn == 0); // 等待按鈕釋放
if (motorRunning)
{
motorRunning = 0;
motorPort = 0x00; // 停止電機(jī)
}
}
if (cwBtn == 0) // 如果按下了順時(shí)針按鈕
{
while (cwBtn == 0); // 等待按鈕釋放
clockwiseDirection = 1; // 設(shè)置電機(jī)啟動(dòng)方向?yàn)轫槙r(shí)針
}
if (ccwBtn == 0) // 如果按下了逆時(shí)針按鈕
{
while (ccwBtn == 0); // 等待按鈕釋放
clockwiseDirection = 0; // 設(shè)置電機(jī)啟動(dòng)方向?yàn)槟鏁r(shí)針
}
}
}
// 延時(shí)函數(shù)
void delay(unsigned int time)
{
unsigned int i, j;
for (i = time; i > 0; i--)
{
for (j = 110; j > 0; j--); // 指令周期延時(shí)
}
}
// 控制步進(jìn)電機(jī)旋轉(zhuǎn)
void motorRotate(unsigned char direction, unsigned int steps)
{
unsigned int i;
for (i = 0; i < steps; i++)
{
if (!motorRunning)
break;
if (direction == clockwise)
{
motorPort = motorSequence[i % 8];
}
else if (direction == counterclockwise)
{
motorPort = motorSequence[7 - (i % 8)];
}
delay(2); // 每步之間的延時(shí),可根據(jù)需要調(diào)整
}
motorPort = 0x00; // 停止電機(jī)
}
在以上代碼中,增加了 cwBtn
和 ccwBtn
兩個(gè)按鍵引腳,并定義為 P2^2
和 P2^3
。按下順時(shí)針按鈕時(shí),將 clockwiseDirection
設(shè)置為 1,表示啟動(dòng)方向?yàn)轫槙r(shí)針;按下逆時(shí)針按鈕時(shí),將 clockwiseDirection
設(shè)置為 0,表示啟動(dòng)方向?yàn)槟鏁r(shí)針。