PMXサーボを使ってみよう C#Lib「MotorWRITE(速度制御、他)編」
前回までの解説で、MotorWRITEコマンドを使用して位置制御でPMXサーボを動かしました。今回の記事は、同じくMotorWRITEコマンドを使用して速度制御、電流制御、トルク制御、PWM制御の動作方法を解説します。
この記事は、以前の記事の続きになります。『PMXサーボを使ってみよう C#Lib「MotorWRITE(位置制御)編」』をご一読いただいてから下記の解説をお読みください。
【関連記事】
PMXサーボを使ってみよう C#Lib「MemWRITE編」
PMXサーボを使ってみよう C#Lib「MotorWRITE(位置制御)編」
PMXサーボを使ってみよう C#Lib「MotorWRITE (組み合わせ制御)編」
この記事で解説するC#向けライブラリ、及びサンプルプログラムは、下記のページからダウンロードしてください。
PMXシリーズのサーボモータを制御するためのオンラインマニュアルを公開しています。PMXサーボを制御するための詳しい情報が記載されていますので、下記の解説と一緒にご一読ください。
■【使用例】速度制御で移動するロボット
以下の車輪駆動のロボットは車輪の動力としてサーボを搭載しています。車輪には左右移動もできるメカナムホイールを採用しました。このロボットはデモンストレーション用にギヤ比の異なるサーボを混在して使用しています(PMX-5203 x 3 , PMX-5204 x 1)。通常であれば、回転速度が異なるサーボを使用しているためまっすぐ走ることはできませんが、各サーボが同じ回転数で動作するように指示することができるため、直進、左右移動など指示通り移動することができます。
■制御方法を選択する方法
まずは、サーボを動かす前にサーボの制御方法を指定します。PMXサーボの制御方法は、メモリマップの「制御モード」をMemWRITEコマンドで書き換えることで選択することができます。
1 2 3 |
byte controlMode = (byte)ControlMode.Speed; // 速度制御モード値 ushort flag = pmx.setControlMode(ServoID, controlMode, 1); Console.WriteLine("setControlMode 0x{0}", flag.ToString("x")); |
Bit0:位置制御
Bit1:速度制御
Bit2:電流制御
Bit3:トルク制御
Bit4:PWM制御
Bit5:移動時間指示
各ビットを1にすることでモードを選択することができます。
速度制御を選択する場合は0x02(0b00000010)を指定します。同じように電流制御は0x04、トルク制御は0x08、PWM制御は0x10になります。
ライブラリ内に予め宣言された変数がありますので、サンプルでは「ControlMode.Speed」のようにそちらの変数を読み出してモードを指定していますが、数値で直接指定しても同じように処理されます。
ライブラリでは、setControlMode()という制御モードを変更するための専用の関数を用意しています。
「制御モード」のデータは、後のMotorWRITEコマンドやMotorREADコマンドでも使用しますので、「controlMode」変数に代入してから引数にしています。直接数値を記入しても同様の処理を実行できます。
制御モードの組み合わせは制限があります。「制御モード」について詳しくはオンラインマニュアルの『制御モード』をご参照ください。
■動作を指示する方法
どの制御モードでもPMXサーボへの動作指示はMotorWRITEコマンドを使用します。関数も前回の記事から変わりません。
1 2 3 4 5 6 7 8 9 10 11 12 13 |
int val = 1000; // 速度制御の第1引数は速度(x10 deg/s) flag = pmx.MotorWRITESingle(ServoID, val, receiveMode, out receiveData, controlMode); Console.WriteLine("MotorWRITE(Single) 0x{0}", flag.ToString("x")); Console.WriteLine("[" + string.Join(", ", receiveData) + "]"); // 指定した時間の間回転させます。 await Task.Delay(3000); // 動作を停止します。 val = 0; flag = pmx.MotorWRITESingle(ServoID, val, receiveMode, out receiveData, controlMode); Console.WriteLine("MotorWRITE(Single) 0x{0}", flag.ToString("x")); Console.WriteLine("[" + string.Join(", ", receiveData) + "]"); |
上記の通りMotorWRITEコマンドを送信することで回転し、await Task.Delay()で処理が一時停止した後、再びMotorWRITEコマンドで0を送信すると動作が停止します。
各モードで指令値に対する単位が異なります。例えば、各モードで指令値1000を指定した場合は下記のように処理されます。
速度制御モードで動作する場合は、1000を指定すると100[°/s]で動作します。「°/s」とは、1秒間に何度移動できるかを表しています。つまり1000を指定した場合は、1秒間に100°移動する速度で回転します。
電流制御モードの場合は、モータの消費電流が1000[mA]を維持するように回転します。
トルク制御モードの場合は、モータの出力が1[N・m]を維持するように回転します。
PMX制御モードは、サーボ内のモータのPWMデューティー比を直接指定することができます。単位は[1/100%]ですので、10%のデューティー比で回転し続けます。
いずれの制御モードでも、指令値をマイナスにするとCCW方向(反時計回り)に回転します。つまり、速度制御の場合は、-1000を指定すると100[°/s]で反時計回りに回転します。
このように、異なる制御モードの状態でも、同じMotorWRITEコマンドで制御することが可能です。
■プログラム全体
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 |
// PMXを通信するクラスを使えるようにする using PMX; // クラスをインスタンス化 PmxSerialClass pmx = new(); ///通信の設定項目 string comName = "COM4"; int pmxBaudrate = 115200; int pmxTimeout = 1000; byte ServoID = 0; // サーボのID番号 // 通信ログを表示させる(表示:True,非表示:False) pmx.logOutput = false; // COMを開く bool openFlag = pmx.open(comName, baudrate: pmxBaudrate, timeout: pmxTimeout); if (openFlag == false) { Console.WriteLine("Serial not open. Exit program"); Environment.Exit(0); } else { Console.WriteLine("Serial Connect success"); } // 制御モードの設定します // writeOpt=0x01のときはトルクONでも強制的に書き込めます(デフォルト値は0x00) // 以下の各ビットを1にすると制御モードとして指定できます // Bit7:0 Bit6:0 Bit5:移動時間 Bit4:PWM Bit3:トルク Bit2:電流 Bit1:速度 Bit0:位置 byte writeOpt = 1; byte controlMode = (byte)ControlMode.Speed; // 速度制御モード値 ushort flag = pmx.setControlMode(ServoID, controlMode, writeOpt); Console.WriteLine("setControlMode 0x{0}", flag.ToString("x")); // 応答データ指定します // writeOpt=0x01のときはトルクONでも強制的に書き込めます(デフォルト値は0x00) // 以下の各ビットを1にすると応答データとして指定できます // Bit7: 入力電圧 Bit6:CPU温度 Bit5:モータ温度 Bit4:PWM出力 Bit3:推定トルク Bit2:電流 Bit1:速度 Bit0:位置 // byte receiveMode = (byte)ReceiveDataOption.Position; // 位置情報を返す byte receiveMode = (byte)ReceiveDataOption.Full; // すべて返す // byte receiveMode = 0xff; // 数値でも指定できます。 flag = pmx.setMotorReceive(ServoID, receiveMode, writeOpt); Console.WriteLine("setMotorReceive 0x{0}", flag.ToString("x")); // サーボのトルクをオンにします flag = pmx.setMotorTorqueOn(ServoID, receiveMode, out int[] receiveData, controlMode); Console.WriteLine("setMotorTorqueOn 0x{0}", flag.ToString("x")); // MotorWRITESingle(組合せ1個)で動作指令 int val = 1000; // 速度制御の第1引数は速度(x10 deg/s) flag = pmx.MotorWRITESingle(ServoID, val, receiveMode, out receiveData, controlMode); Console.WriteLine("MotorWRITE(Single) 0x{0}", flag.ToString("x")); Console.WriteLine("[位置, 速度, 電流, 推定トルク, PWM出力, モータ温度, CPU温度, 入力電圧]"); // 対応していない応答データの返り値は異常値が入ります Console.WriteLine("[" + string.Join(", ", receiveData) + "]"); // 指定した時間の間回転させます。 await Task.Delay(3000); // 動作を停止します。 val = 0; flag = pmx.MotorWRITESingle(ServoID, val, receiveMode, out receiveData, controlMode); Console.WriteLine("MotorWRITE(Single) 0x{0}", flag.ToString("x")); Console.WriteLine("[位置, 速度, 電流, 推定トルク, PWM出力, モータ温度, CPU温度, 入力電圧]"); // 対応していない応答データの返り値は異常値が入ります Console.WriteLine("[" + string.Join(", ", receiveData) + "]"); // トルクスイッチ:Free flag = pmx.setMotorFree(ServoID); Console.WriteLine("setMotorFree 0x{0}", flag.ToString("x")); // COMを閉じる pmx.close(); |
全体の流れは、前回の記事で解説した位置制御と同じです。「制御モード」と「応答データ指定」を指定し、サーボのトルクをONにしてからMotorREADコマンドで動作します。
応答データ指定、トルクONに関しましては変更ありませんので前回の記事をご参照ください。
■指令値の制限値
サーボの性能を超えて動作しないように、PMXサーボには各指令値、設定値に制限値が設けられています。制限値は、メモリマップの600番台を読み出すことで確認することができます。ライブラリには、各制限値を読み出す関数として入力電圧の最大値の指定範囲を読み出すgetMaxVoltageRange()など専用の関数を用意しています。例としてPMX-SCR-5204HVの場合、制限値は下記のようになっています。
【PMX-SCR-5204HVのprintAllRange結果】
中央値オフセット設定範囲(600)[x100deg]>> 0x00 [-17999, 18000]
下限電圧リミット設定範囲(604)[mV]>> 0x00 [8000, 12000]
上限電圧リミット設定範囲(608)[mV]>> 0x00 [12000, 16000]
電流リミット設定範囲(616)[mA]>> 0x00 [0, 3800]
モータ温度リミット設定範囲(620)[x10℃]>> 0x00 [0, 1000]
CPU温度リミット設定範囲(624)[x10℃]>> 0x00 [0, 1000]
CW方向設定範囲(628)[x100deg]>> 0x00 [-32000, 32000]
CCW方向設定範囲(632)[x100deg]>> 0x00 [-32000, 32000]
最大速度指令値設定範囲(636)[x10deg/s]>> 0x00 [0, 3800]
最大電流指令値設定範囲(640)[mA]>> 0x00 [0, 3800]
最大トルク指令値設定範囲(644)[mN.m]>> 0x00 [0, 6800]
速度や電流値など指令する場合は、上記の範囲を超え内容の気を付けて使用してください。PMX-SCR-5204HVに対して速度を指定する場合は、0~3800が設定範囲です。これは、逆転を指定するための-3800も範囲に含まれますので、正確には-3800~0~3800の範囲で指定することができます。
範囲を超えますと、受信パケットのステータスが「データエラー」のフラグが立ち、処理が実行されません。
以上で、速度制御など位置制御以外の制御モードに関する解説を終わります。制御モードを変更することで、組み込む箇所に合わせた動作を指定することが可能です。
前の記事『PMXサーボを使ってみよう PCから制御「MotorWRITE (組み合わせ制御)編」』
PMX-SCR-9203HVの詳細をみる PMX-SCR-9204HVの詳細をみる PMX-SCR-5203HVの詳細をみる PMX-SCR-5204HVの詳細をみる