バージョン情報
Arduino IDE 1.0.6 ,windows 8.1
Arduinoスレーブの第2弾:サーボをシリアル通信のスレーブとして動くようにしてみてた。
第1弾はこちら<Arduino スレーブその1: 1桁7セグ>
PCや他のArduinoなどから”文字列”でコマンドを送信し、スレーブ側で受信した文字列を解析して動作するようにしてみた。
材料
・Arduino pro mini 328 5V
・タクトスイッチ(手動動作確認用)
・サーボモータ SG90
回路
ソースコード
アクションの種類と数値を文字列で結合したものを、コマンドとして処理しようと思ったら結構はまった。
【はまりポイント】
・switch case で文字列が使えない?
・splitが使えない?
・自作関数の引数、戻り値に文字列が使えない?
いろいろ手段はありそうだが、今回は強引に以下の手段で乗り切ることにした。(クラスを作ったほうがいいんだろうけど)
・Stringオブジェクトをグローバル変数で使う。
・if ~ else if ~ を羅列する。
・”100_action”のように数値の後ろにアクションの種類を書くことにして、アクションの種類の判定には、string.endsWidth()を使い、数値の取得にはatoi()を使う。
//スレーブ:サーボ
#include <Servo.h>
#define servo_1 9
#define button_1 11
#define button_2 12
String str_cmd = "";
Servo myservo_1;
int angle = 90;
void setup() {
myservo_1.attach(servo_1);
pinMode(button_1, INPUT_PULLUP);
pinMode(button_2, INPUT_PULLUP);
Serial.begin(115200);
}
void loop() {
//マスターから受信したら
if(myReadLine() > 0){
Serial.println(str_cmd);
action_servo();
}
//ボタンで手動操作
if (digitalRead(button_1) == 0){
angle = min(angle + 10,180);
myservo_1.write(angle);
}
if (digitalRead(button_2) == 0){
angle = max(angle - 10,10);
myservo_1.write(angle);
}
delay(20);
}
int myReadLine(void){
int cnt_buf = 0;
str_cmd = "";
char ch;
//受信したら
if(Serial.available() > 0){
delay(100);
cnt_buf = Serial.available();
for (int iii = 0; iii < cnt_buf; iii++){
ch = Serial.read();
str_cmd.concat(ch);
}
}
return cnt_buf;
}
//サーボアクション
void action_servo(void){
if(str_cmd.endsWith("action")){
char chA[5];
str_cmd.toCharArray(chA,4);
myservo_1.write(constrain(atoi(chA),10,180));
}else if(str_cmd == "play"){
myservo_1.write(90);
}else if(str_cmd == "back"){
myservo_1.write(10);
}else if(str_cmd == "forward"){
myservo_1.write(180);
}
delay(20);
}
動作確認
Arduino IDEのシリアルモニタからコマンドを送信して動作確認。






「Arduino スレーブその2:サーボ」への1件のフィードバック