適当に書いたスケッチです。正しくないかも知れません。無保証です。
Aruduino nanoとステッピングモータドライバ、タクトスイッチ、小型LCDの接続はスケッチの先頭に#defineしています。スイッチの反対側のピンはGNDです。
時計の秒針のように精確な1rpm(回転/60秒)を実現するために、Timer1割り込みでパルスを作って回転/5秒(12rpm)を基準にしています。1回転4秒でも回りましたが、5秒の倍数にしたほうがrpmを細かく分けられたのでこうしました。
//------------------------------------------------------------------ // 21.07.07 naka // ステッピングモータのテスト // P1-P4: ステッピングモータのドライバの各ピン // SW1 : タクトスイッチ(アクティブLow) 回転方向切り替え // SW2 : タクトスイッチ(アクティブLow) 回転角度切り替え(+90度)0度は連続回転 // SW3 : タクトスイッチ(アクティブLow) 回転RPM切り替え(1~12) // SW4 : タクトスイッチ(アクティブLow) Start/Stop // SDAPIN,SLCPIN : 小型液晶ディスプレイのI2C // // Timer1割り込みで5秒/回転(2,048Step)するパルス409.6Hzを生成 //------------------------------------------------------------------ #define P1 2 #define P2 3 #define P3 4 #define P4 5 #define SW1 6 #define SW2 7 #define SW3 8 #define SW4 9 #define SDAPIN A4 #define SCLPIN A5 #include <FaBoLCDmini_AQM0802A.h> FaBoLCDmini_AQM0802A lcd; #define steps_per_rotation 2048 volatile int timer1_flag; volatile int ph_cnt,rpm_cnt,deg_cnt; int rpm_i,rpm_mag,dir; long deg,deg_step; int run_flag; int rpm_tbl[6][2] = {1,12, // 1rpm, 5秒を12倍 2,6, // 2rpm 3,4, // 3rpm 4,3, // 4rpm 6,2, // 6rpm 12,1}; //12rpm, 1: 5秒/回転(これが基準) void setup() { pinMode(P1, OUTPUT); pinMode(P2, OUTPUT); pinMode(P3, OUTPUT); pinMode(P4, OUTPUT); pinMode(SW1, INPUT_PULLUP); pinMode(SW2, INPUT_PULLUP); pinMode(SW3, INPUT_PULLUP); pinMode(SW4, INPUT_PULLUP); motor_off(); ph_cnt = 0; // Timer1設定 TCCR1A = 0; TCCR1B = 0; // 5秒/回転 2048/5 = 409.6Hz // 1/409.6 = 0.00244140625 sec // 0.00244140625*16MHz = 39,062.5 (0.5は割り込み交互に吸収) TCNT1 = 26474; // offset 65536-39062 = 26474 と // 65536-39063 = 26473 を交互 TCCR1B |= (1 << CS10); // プリスケーラ 1 // モニタLCD設定 SetupLCD(); dispLCD_start(); rpm_cnt = 0; rpm_i = 0; rpm_mag = rpm_tbl[rpm_i][1]; // 基準5秒/回転の倍数 dir = 0; // 右回転 deg = 0; // 90度 deg_step = steps_per_rotation * deg / 360; // ステップ数 deg_cnt = 0; dispLCD(); run_flag = 0; TIMSK1 |= (1 << TOIE1); // Timer1イネーブル } byte ph1[4][4] = { // 1相励磁 1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1 }; ISR(TIMER1_OVF_vect) { if (timer1_flag==1) TCNT1 = 26474; else TCNT1 = 26473; timer1_flag ^= 1; rpm_cnt+=1; if(run_flag==1 && rpm_cnt==rpm_mag) { if (deg_cnt<deg_step || deg_step==0) { digitalWrite(P1,ph1[ph_cnt][0]); digitalWrite(P2,ph1[ph_cnt][1]); digitalWrite(P3,ph1[ph_cnt][2]); digitalWrite(P4,ph1[ph_cnt][3]); if (dir==0) ph_cnt = (ph_cnt+1)%4; else { ph_cnt -= 1; if(ph_cnt<0) ph_cnt = 3; } rpm_cnt = 0; deg_cnt++; } else if (deg_cnt == deg_step) { // 規定数回転したのでstop run_flag = 0; motor_off(); } } } void loop() { checkSW(); // タクトスイッチ状態確認 } void checkSW() { if (digitalRead(SW1)==LOW) { // direction dir ^= 1; // 回転方向逆転 dispLCD(); while(digitalRead(SW1)==LOW); } else if (digitalRead(SW2)==LOW) { // rpm rpm_i = (rpm_i+1)%6; rpm_mag = rpm_tbl[rpm_i][1]; rpm_cnt = 0; dispLCD(); while(digitalRead(SW2)==LOW); } else if (digitalRead(SW3)==LOW) { // degree deg += 45; if (deg>360) deg = 0; deg_step = steps_per_rotation * deg / 360; deg_cnt = 0; dispLCD(); while(digitalRead(SW3)==LOW); } else if (digitalRead(SW4)==LOW) { // Start/Stop run_flag ^= 1; if (run_flag==0) motor_off(); deg_cnt = 0; rpm_cnt = 0; while(digitalRead(SW4)==LOW); } delay(10); // チャタリング回避 } void motor_off() { digitalWrite(P1,LOW); digitalWrite(P2,LOW); digitalWrite(P3,LOW); digitalWrite(P4,LOW); } void dispLCD_start() { lcd.clear(); lcd.print("STEPPING"); lcd.setCursor(0, 1); // Col,Raw lcd.print(" MOTOR"); delay(1000); dispLCD(); } void dispLCD() { char buff[10]; char dir_txt[2]; if (dir) strcpy(dir_txt,"L"); else strcpy(dir_txt,"R"); lcd.clear(); lcd.setCursor(0, 0); // Col,Raw sprintf(buff,"%s %3dDEG",dir_txt,deg); lcd.print(buff); lcd.setCursor(0, 1); // Col,Raw sprintf(buff," %2dRPM",rpm_tbl[rpm_i][0]); lcd.print(buff); } void SetupLCD() { lcd.begin(); lcd.command(0x38); lcd.command(0x39); lcd.command(0x14); lcd.command(0x73); lcd.command(0x51); // 5V // lcd.command(0x56); // 3.3V delay(2); lcd.command(0x6c); delay(300); lcd.command(0x38); delay(1); lcd.command(0x01); delay(2); lcd.command(0x0c); delay(2); } //------------------------------------------------------------------ // EOF //------------------------------------------------------------------
0 件のコメント:
コメントを投稿