前回、マイクロサーボSG90をArduinoで動かしてみました。
今回は、360度連続回転可能なマイクロサーボFS90Rを試してみたいと思います。
- Arduino NANO(互換品)
- サーボモーターFS90R
- タイヤ(FS90R対応)
- モーター用電源(単3x4本)
- ブレッドボード
- ジャンパーワイヤ
部品等の購入先リンクは記事の一番下に記載してあります。
サーボモーターFS90Rについて
前回のSG90は、「可動域が180°で、指定した角度(位置)まで回転してとまる」ものでした。今回試してみるFS90Rは、「可動域が360°で、指定した速度でぐるぐる連続回転する」ものとなります。
パルス幅の範囲は700μs~2300μsで、静止点は1500μsとなります。パルス幅が静止点以上の場合は反時計回りに回転し、パルス幅が長くなると回転速度が増加、反対にパルス幅が静止点以下の場合は時計回りに回転し、パルス幅が短くなると速度が増加します。なお、静止点の位置は、小型のド裏側のポテンショメーターを回すことで調整できます。
ArduinoでサーボモーターFS90RをPWM制御してみる
SG90の時と同様、モーター用の電源は別電源として(Arduinoの電源は省略)、信号線はデジタルピンD7としました。
時計回りに回転 => 停止 => 反時計回りの順で動かす
PWMによる制御の考え方は前回の記事「ArduinoでマイクロサーボSG90を動かしてみる」を見てください。
SG90の場合は、モーターのスピードを0~100の範囲で、時計回りは正、反時計回りは負の数で指定できるよう、関数化しました。
スケッチ
const int SERVO_PIN = 7;
void motor_servo(int motor_speed, int seconds) {
int pulse_width = 1500-motor_speed*8;
int starttime = millis();
while(true) {
if (millis()-starttime > seconds) break;
digitalWrite(SERVO_PIN, HIGH);
delayMicroseconds(pulse_width);
digitalWrite(SERVO_PIN, LOW);
delay(20);
}
}
void setup() {
pinMode(SERVO_PIN, OUTPUT);
}
void loop() {
motor_servo(100,1000);
motor_servo(0,1000);
motor_servo(-100,1000);
motor_servo(0,1000);
servoライブラリを使って制御してみる
SG90の時と同様に、Arduinoのサーボモーターを制御するservoライブラリを使ってみます。PWMパルス生成部分をライブラリが処理してくれるのですが、「指定した角度(位置)まで回転してとまる」SG90とは異なり、FS90Rは、「指定した速度でぐるぐる連続回転する」ものとなりますので、スピードと回転方向を「%」で指定できると感覚的に分かりやすいと思います。ですので、回転方向とスピードを「角度」に変換する関数も作ってみました
ライブラリのインクルード
スケッチ先頭に、「#include
インスタンス生成
サーボモーターを使えるように、インスタンスを生成します。スケッチ例では、「motor_servo」としています。
出力ピン割り当て(attach)
PWMの出力ピンを割り当てます。スケッチ例ではデジタルピンD7を使用しています。パラメータは(ピン番号,min, max)の3つで後ろの2つは省略可能です。「min」はサーボの角度が0度のときのパルス幅[us]で、デフォルトは544。「max」はサーボの角度が180度のときのパルス幅[us]で、デフォルトは2400。
指定した回転方向・スピードで動かす(write)
回転方向とスピードを0-180の値で指定すると、そのスピードにするためのパルスが「attach」で指定したピンから出力されます。90を指定するとモーターは静止し、90より小さくすると時計回り方向に回転し、0へ近づくほど速く回転します。逆に90より大きくすると反時計回りに回転し、180へ近づくほど速く回転します。
指定したパルス幅で動かす(writeMicroseconds)
サーボモータへの出力を、0~180の値ではなくパルス幅(マイクロ秒)で指定します。サーボモータに与えられるパルスは20ms周期で、1周期中のHigh時間を直接指定します。出力したいパルス幅(μs)の範囲は「1~19999」で「0」を指定すると出力OFFとなります。
スケッチ
#include <Servo.h>
Servo motor_servo;
void motor_speed(int pct) {
int angle = 90-0.9*pct;
motor_servo.write(angle);
}
void setup() {
motor_servo.attach(7,700,2300);
}
void loop() {
motor_speed(100);
delay(2000);
motor_speed(0);
delay(2000);
motor_speed(-100);
delay(2000);
motor_speed(0);
delay(2000);
}
部材購入先リンク
モーターとタイヤは秋月の方が安いです。