目的
使用8051晶片控制步進馬達正/反轉,並且加入啟動加速的機制,防止啟動磁激過快,造成步進馬達一開始就失速
使用晶片
控制晶片:8051
驅動晶片:L298N
發生的錯誤
(1)問題:磁激不正常
由於使用的控制器為已經整合好的L298N的驅動模組
但似乎有一個 Port 有問題,因此在送出磁激時會不正常轉動
因此花費了許多時間
解決:更換新的 L298N 驅動模組
(2)問題:轉矩不夠力,無法推動光碟機的
一開始使用單相磁激,對於推動光碟機的傳動是不夠力的
解決:更改為 2相磁激
/* 使用2相磁激 */
/* b-b a-a */
/* 0x09 = 0000 0 0 1 1 */
/* 0x05 = 0000 0 1 0 1 */
/* 0x06 = 0000 0 1 1 0 */
/* 0x0a = 0000 1 0 0 1 */
(3)問題:磁激後一直抖動
因送出磁激後,會等待多久 time 次數後,才會進行下一次
的激磁,但因為送出後對於該相位仍不斷的進行磁激,因
此造成不斷的對同一個相位磁激,造成不斷的抖動
解決:於沒有正反轉需求時對 P1 送出 0x00
8051 Code
#include void _motor_enabled() ; /* Port m*/ /* motor_stop_flag run=1 stop=0 */ bit _motor_stop_flag; /* P1_5 on =1 stop=0 */ sbit _motor_forward_flag = P1^4; /* P1_6 on =1 stop=0 */ sbit _motor_receive_flag = P1^5; unsigned char _cycle[4] = {0x09,0x05,0x06,0x0a} ; /* 使用2相磁激 */ /* b-b a-a */ /* 0x09 = 0000 0 0 1 1 */ /* 0x05 = 0000 0 1 0 1 */ /* 0x06 = 0000 0 1 1 0 */ /* 0x0a = 0000 1 0 0 1 */ /* 單相磁激...留著備用 */ /* unsigned char _cycle[4] = {0x01,0x02,0x04,0x08}; */ unsigned int _times; /* 速度用變數 */ unsigned short _motor_speed_time ; /* 速度用變數 */ unsigned short _magnetic ; /* 加速計算磁激用變數 */ unsigned short _speed ; /* 速度次數變數 */ unsigned short _speed_count; /* 加速計算用變數 */ main() { /* P1 輸出全部歸 0 */ P1 = 0x00; /* _motor_enabled 啓動 */ _motor_enabled(); while(1); } void _motor_enabled() { /* 1000 = 1 ms (1 sec = 1000 ms) */ _motor_speed_time = 1000; /* timer mode 1 */ TMOD = 0x01; /* setup timer0 TH0 values */ TH0 = ( 65536 - _motor_speed_time ) / 256 ; /* setup timer0 TL0 values */ TL0 = ( 65535 - _motor_speed_time ) % 256 ; /* all interrupt enable */ EA = 1; /* timer 0 interrupt enable */ ET0 = 1; /* timer0 start */ TR0 = 1; _speed = 1; _speed_count = 0; } void timer0_int(void) interrupt 1 { /* k 變數用來儲存 _times /4 目前相位 */ /* x 變數用來儲存 _cycle[k] 陣列中資料 */ static unsigned char x,k; /* TH0 計時器值設定 */ TH0 = ( 65536 - _motor_speed_time ) / 256 ; /* TL0 計時器值設定 */ TL0 = ( 65535 - _motor_speed_time ) % 256 ; if(_motor_forward_flag == 1 || _motor_receive_flag == 1) /* 正/反轉任一被按下時,進入執行 */ { /* 加速判斷區 - 開始 */ /* 加速計算 +1*/ _speed_count ++; /* 當加速 = 速度次數時進入 */ if(_speed == _speed_count) { /* 加速計算歸 0 */ _speed_count=0; /* 加速計算磁激 < 24 時才進入判斷加速需求 */ if( _magnetic < 24 ) /* 加速計算磁激 + 1 */ _magnetic ++; /* 加速計算磁激大於0 小於 8 _speed = 6 */ if( _magnetic >= 0 && _magnetic <= 8) _speed = 6; else /* 加速計算磁激 大於9 小於 16 _speed = 4 */ if( _magnetic >= 9 && _magnetic <= 16) _speed = 4; else /* 加速計算磁激 大於17 小於 24 _speed = 2 */ if( _magnetic >= 17 && _magnetic <= 24) _speed = 2; else /* 最終大於 24 _speed =1 */ _speed = 1; /* _time 次數 /4 取得目前磁激相位 */ k = (_times%4); /* 將目前相位放入 x 變數中,並 & 0X0F */ x = (_cycle[k] & 0x0f); /* 正轉 +1 反轉 -1 */ if(_motor_forward_flag == 1) _times ++; else if(_motor_receive_flag == 1) _times --; /* 送出磁激至 P1 */ P1 = x; } } else { /* 正/反轉未被按下時 */ /* reset _speed = 1*/ _speed = 1; /* reset _speed_count = 0*/ _speed_count = 0; /* reset _magnetic = 0 */ _magnetic =0; /* 不需磁激時送出0x00,否則 motor 會一直抖 */ P1 = 0x00; } }