Arduino Robot with PS2 Controller(PlayStation 2 Joystick)
コンポーネントと消耗品
> |
| × | 1 | |||
| × | 1 | ||||
| × | 1 | ||||
| × | 1 |
アプリとオンラインサービス
> |
|
このプロジェクトについて
このチュートリアルでは、ワイヤレスPlayStation 2(PS2)ジョイスティックを使用してロボット戦車を操縦する方法を紹介します。このプロジェクトの中核には、ArduinoUnoボードが使用されました。ワイヤレスコントローラーからコマンドを受信し、モーターの速度を設定します。他の開発ボード(NodeMCU、Firebeetleなど)も使用される可能性があり、このチュートリアルで提示されている原則は、ロボットやガジェットの他のモデルに適用できます。
私は以前、Blynk制御のロボットタンクを設計しました。 Wi-Fiネットワークに接続し、Blynkサーバーからコマンドを受信します。 Blynkアプリを実行しているスマートフォンがリモコンとして使用され、プッシュボタン、スライドバー、さらにはスマートフォンの加速度計など、さまざまな入力方法が使用されました。このプロジェクトの詳細については、https://www.hackster.io/igorF2/wi-fi-managed-robot-using-wemos-d1-esp8266-and-blynk-464198
をご覧ください。また、音声コマンドを使っていくつかの実験を行いました。手を使わずにロボットを遠隔操作したい場合や、動きが制限されている人がロボットにアクセスできるようにしたい場合に便利です。たとえば、ロボットによる音声制御の車椅子を考えるかもしれません。 DIYロボットキットが、私のお気に入りのツールであるAdafruit.io、IFTTT、ArduinoIDEとともに使用されました。詳細な手順はこちら:
https://www.hackster.io/igorF2/wi-fi-voice-driven-robot-using-google-assistant-79802c
3Dプリンターやレーザー切断機などの複雑なツールを使用しなくても、さまざまなキットを使用したり、単純な材料を使用して独自のロボットを設計したりすることができます。以前のチュートリアルの1つに例があります:
https://www.hackster.io/igorF2/widc-wi-fi-driven-fpv-robot-8f1e09
ステップ1:ツールと材料
このプロジェクトでは、次のツールが使用されました。
- はんだごてとワイヤー (リンク/リンク)。 DCモーターには、すでに端子にはんだ付けされたワイヤーが付属しています...しかし、最終的には破損し、再はんだ付けする必要がある場合があります。ですから、良いはんだごてとワイヤーを近くに置くことを検討してください。
- EVAフォームシート (または他の非導電性材料)。このプロジェクトで使用したロボットシャーシはアルミ製で、この金属部品に回路基板が取り付けられています。短絡の可能性を避けるために、ボードと金属プレートの間にフォームシートの層を使用しました。
- 両面テープ 。フォームシートを回路基板に接着するため、およびHブリッジモジュールを取り付けるために使用されました。
- はさみ 、いくつかのフォームシートの長方形をカットするため。
プロジェクトでは次のハードウェアパーツを使用しました:
- ArduinoUnoベースの開発ボード (リンク/リンク/リンク/リンク)。ロボットのメインコントローラーとして使用されます。 Arduino IDEを使用すると、非常に使いやすくプログラミングが簡単で、電子機器やプログラミングの初心者に最適です。
- L298NデュアルチャネルHブリッジモジュール (リンク/リンク/リンク/リンク)。このモジュールを使用すると、Wemos(またはArduino)からの3.3V信号を、モーターに必要な12Vに増幅できます。
- DIYロボットシャーシタンク (リンク)。この素晴らしいキットには、2つのDCモーター、ギア、トラック、ボルト、ナットなど、タンクを構築するために必要なすべてのものが含まれています。シャーシの組み立てに必要なツールがすでに付属しているため、初心者に最適です。
- PS2ワイヤレスリモコン (リンク)。このビデオゲームコントローラーは、コマンドをワイヤレスで受信機に送信できます。受信機は、シリアル通信を使用してマイクロコンピューターと接続できます。
- 18650 3.7Vバッテリー(x3) (リンク/リンク)。私は回路全体に電力を供給していました。このタンクは12Vモーターを使用しています。私はそれらに電力を供給するために3つの3.7Vバッテリーを直列に使用しました。
- 3S18650バッテリーホルダー (リンク/リンク/リンク)。直列に3つの18650バッテリーを収納でき、タンクの背面に簡単に取り付けることができます。
- 18650バッテリー充電器 (リンク/リンク)。バッテリーは最終的に電力が不足します。それが起こるとき、バッテリー充電器はあなたの救助に来るでしょう。
- ジャンパー (リンク/リンク)。私は、hブリッジとWemosの間の信号に6つのオス-メスジャンパーを使用し、5VとGndに2つのオス-オスジャンパーを使用しました。いくつかのセンサーを追加する予定がある場合は、さらに必要になる可能性があります。
- タイプBUSBケーブル 。コードをアップロードするためにこれが必要になります。ほとんどのボードには、すでに独自のケーブルが付属しています。
上記のリンクは、このチュートリアルで使用されているアイテムを見つけることができる場所の提案にすぎません(そしておそらく私の将来のチュートリアルをサポートします)。他の場所で自由に検索して、お気に入りのローカルストアまたはオンラインストアで購入してください。
ステップ2:ロボットの組み立て
このプロジェクトの最初の部分は、ロボット構造の組み立てでした。
以前のプロジェクトでは、簡単にアクセスできる材料を使用して、自分のロボットの構造を開発しました(複雑なツール、3Dプリンター、レーザー切断機は必要ありません)。このプロジェクトは以下のリンクにあります:
https://www.hackster.io/igorF2/widc-wi-fi-managed-fpv-robot-8f1e09
その後、オンラインストアから入手したロボットキットのチャンスを与えることにしました。ロボットシャーシへのリンクは、次のリンクにあります:http://bit.ly/2ycI8fP。キットをお探しの方にはいいオプションだと思います!以下のリンクでわかるように、他の2つのチュートリアルで使用しました。
https://www.hackster.io/igorF2/wi-fi-driven-robot-using-wemos-d1-esp8266-and-blynk-464198
https://www.hackster.io/igorF2/wi-fi-voice-driven-robot-using-google-assistant-79802c
最初は、組み立てが複雑になるか、部品の不足などの問題が発生するように見えました(キットを構成する部品の量を考えると)。しかし、このキットは本当に驚きました!すべての部品は私には良質のように見え、いくつかのスペアパーツがキットに付属していました。したがって、ワークベンチの下でネジを紛失しても、プロジェクトを実行できなくなることはありません。これは、優れていることがわかりました(特に、ネジを2本紛失した後)。
もう1つの良い点は、ロボットを取り付けるために必要なすべてのツールがキットに含まれていることです(2つの六角レンチとドライバー)。これにより、ツールがあまりない初心者にとってキットが優れていると思います!
ネガティブな側面として、私はドキュメントの欠如を強調します。ロボットの組み立て人
ual(中国語のスプレッドシートファイル)は非常にユーザーフレンドリーではなく、その戦車のオンラインチュートリアルはあまりありません。そこで、ロボットを組み立てるプロセスを上のビデオに記録することにしました。もう1つの注意点は、ロボット構造の材質に関するものです。ベースはすべてアルミニウムでできているため、プリント回路基板のピンがフレームに接触すると短絡が発生する可能性があります。
使用できる他のオンラインキットがあります。以下で説明するように、独自の構造を作成することもできます。
ステップ3:回路の配線
ロボットの背面には、3つの18650バッテリーで作られたパワーパックが取り付けられました。ロボットに11.1V(3 x 3.7V)を供給します。 12VDCモーターに電力を供給するのに十分です。
モーターの制御には、L298NデュアルチャネルHブリッジを使用しました。 Arduinoボードの5V信号を受信し、モーターにより高い電圧を供給します。また、モーターを両方向に回転させ、これらの入力信号の組み合わせに依存します。
各デバイスは、回路図に従って接続されました。
接続する必要のあるピンのリストに従います:
Arduino Unoの入力/出力:
- デジタルピン3 => HブリッジENAピン
- デジタルピン5 => HブリッジIN1ピン
- デジタルピン4 => HブリッジIN2ピン
- デジタルピン8 => HブリッジIN3ピン
- デジタルピン7 => HブリッジIN4ピン
- デジタルピン6 => HブリッジENBピン
- 5Vピン=> Hブリッジ5Vピン
- Gndピン=> HブリッジGndピン
- デジタルピン10 => PS2レシーバーピン6
- デジタルピン11 => PS2レシーバーピン2
- デジタルピン12 => PS2レシーバーピン1
- デジタルピン13 => PS2レシーバーピン7
- 3.3Vピン=> PS2レシーバーピン5
- Gndピン=> PS2レシーバーピン4
Hブリッジの入力/出力:
- ENAピン=> Arduinoデジタルピン3
- IN1ピン=> Arduinoデジタルピン5
- IN2ピン=> Arduinoデジタルピン4
- IN3ピン=> Arduinoデジタルピン8
- IN4ピン=> Arduinoデジタルピン7
- ENBピン=> Arduinoデジタルピン6
- 5Vピン=> Arduino5Vピン
- Gndピン=> ArduinoGndピン
- アースピン=>バッテリーパックのマイナス線
- 12Vピン=>バッテリーパックのプラス線
- OUT1 =>右モーターのマイナス線
- OUT2 =>右モーターのプラス線
- OUT3 =>左モーターのプラス線
- OUT4 =>左モーターのマイナス線
PS2レシーバー:
- ピン1(データ)=> Arduinoデジタルピン12
- ピン2(コマンド)=> Arduinoデジタルピン11
- ピン4(アース)=> ArduinoGndピン
- ピン5(電源)=> Arduino3.3Vピン
- ピン6(注意)=> Arduinoデジタルピン10
- ピン7(時計)=> Arduinoデジタルピン13
ステップ4:ArduinoIDEをセットアップする
このプロジェクトでは、ArduinoボードのプログラミングにArduinoIDEを使用しました。
1。 ArduinoIDEの最新バージョンをダウンロードしてインストールします
Windows、Linux、またはMAC OSXの最新バージョンは、ArduinoのWebサイトで見つけることができます:https://www.arduino.cc/en/main/software
無料でダウンロードし、コンピューターにインストールして起動します。
2。ライブラリの追加
このプロジェクトでは、ArduinoPS2Xライブラリを使用しています。
https://github.com/madsci1016/Arduino-PS2Xでライブラリをダウンロードします。ファイルを解凍し、フォルダーをArduinoIDEライブラリ/ツールフォルダーにコピーします。
............
開発環境の準備ができたので、次のステップに進みましょう!
ステップ5:PS2ワイヤレスコントローラーライブラリの説明
PS2ワイヤレスコントローラーは、ロボット工学プロジェクトに最適なツールです。それは信じられないほどの数のボタンを持っています:20のデジタルプッシュボタンと2つのアナログスティック。このように、ロボットを制御する無限の可能性があります。
Bill PorterのPS2Xライブラリ(https://github.com/madsci1016/Arduino-PS2X)を使用して、コントローラーをArduinoUnoボードに接続しました。
これは、ジョイスティックからアナログおよびデジタル入力を読み取るためのいくつかのメソッドを含む、コントローラーのPS2Xクラスを定義します。このクラスのオブジェクトは、次のコードを使用して作成されます(セットアップ前またはセットアップ中):
PS2X ps2x;
オブジェクトを定義したら、次の関数を使用してArduino I / Oピンにリンクする必要があります。
error =ps2x.config_gamepad(clock、command、attention、data、pressure?、rumble?);
接続またはコントローラー自体に問題がある場合、この関数はエラーを返す可能性があります。
ライブラリから使用される主な機能は、デジタルおよびアナログ入力を読み取るための機能です。読み取りとデジタル入力には、次の方法が使用されます。
ps2x.Button(button);
どのボタン 読み取るボタンの名前です。各ボタンは次のようにマップされます:
方向ボタン:
- PSB_PAD_UP =D-パッドアップボタン;
- PSB_PAD_DOWN =D-パッドダウンボタン;
- PSB_PAD_LEFT =D-padの左ボタン
- PSB_PAD_RIGHT =Dパッドの右ボタン
アクションボタン:
- PSB_GREENまたはPSB_TRIANGLE =緑色の三角形のボタン
- PSB_REDまたはPSB_CIRCLE =赤い丸ボタン
- PSB_BLUEまたはPSB_CROSS =青いxボタン
- PSB_PINKまたはPSB_SQUARE =ピンクの四角いボタン
トリガー:
- PSB_L1 =左側のトリガーボタン1
- PSB_R1 =右側のトリガーボタン1
- PSB_L2 =左側のトリガーボタン2
- PSB_R2 =右側のトリガーボタン2
スティック:
- PSB_L3 =左スティックプッシュボタン(はい、スティックをプッシュボタンとして押すことができます)
- PSB_R3 =右スティックプッシュボタン
メニュー:
- PSB_SELECT =選択ボタン
- PSB_START =スタートボタン
スティックのアナログ値(0〜255の整数のコンバーターを使用)を読み取るには、次の方法を使用します。
ps2x.Analog(stick_axis);
stick_axis 次のように、スティックと読み取る方向を表します。
- PSS_LY =左スティックのy位置
- PSS_LX =左スティックのx位置
- PSS_RY =右スティックのy位置
- PSS_RX =右スティックのx位置
これらの基本的な機能を使用すると、プロジェクトでPS2コントローラーを使用する準備が整います。次の手順では、これらのボタンを組み合わせたArduinoスケッチの例をいくつか示します!
ステップ6:スケッチ#1-十字キーボタン
セガマスターシステムやメガドライブ、ニンテンドーSNESなどの古いビデオゲームには、力に敏感なボタンがありませんでした。方向ボタンはオン/オフボタンのみでした。この最初の例では、これらのコンソールの古いビデオゲームで使用されるようなコントロールをエミュレートしたいと思いました。
この最初のスケッチでは、ロボットへの入力として十字キーボタンを使用しました。各ボタンは、ロボットが基本的な動きの1つを実行するために使用しました。前進、右折、左折、または後退です。
これらのボタンにはバイナリ出力があります。このように、マイクロコントローラーはボタンが押されたことだけを理解しますが、ボタンがどれだけ強く押されたかは理解しません。このように、特定のボタンがクリックされると、モーターはフルスピードで動作します。
私の回路図に従ってすべてを接続すると、次の出力が得られます。
- PSB_PAD_UP =前進
- PSB_PAD_DOWN =戻る
- PSB_PAD_LEFT =左折
- PSB_PAD_RIGHT =右折
前にも言ったように、モーターは一定の速度で動きます。左または右に回転すると、モーターは反対方向に回転するため、ロボットはその軸を中心に回転します。
Arduinoコード:
コードをダウンロードして、ArduinoIDEで開きます。私が行ったのと同じピン配置を使用する場合、おそらくコードで何も変更する必要はありません(ただし、モーターの向きが異なる場合は必要になる可能性があります
コードをアップロードするには、「Arduino / Genuino Uno」ボードを選択し、適切なCOMポートを選択し、ボードをコンピューターのUSBポートに接続して、コードをアップロードします。
アップロードが完了したら、USBケーブルを抜き、バッテリー。コードが実行を開始し、ArduinoボードがPS2ジョイスティックを自動的に接続します。初めて使用するときはシリアルモニターを開き、接続状態を確認してください。ジョイスティックとの接続に失敗した場合は、次のことを行う必要があります。
- ArduinoUnoボードをリセットします。何度か試してみてください(私にとっては、通常、3回目のリセット後に機能します)。
- ジョイスティックがオンになっているかどうか(およびバッテリーが充電されているかどうか)を確認します。受信機には、ジョイスティックがペアリングされたかどうかを示すいくつかのLEDがあります。また、ArduinoのRXピンとTXピンが新しいコマンドを受信したときに点滅するかどうかを確認します(そしてシリアルポートのステータスを更新します)。
- 接続を確認してください...コンポーネント間のジャンパーに問題がある可能性があります。
コードの説明:
このプロジェクトでは、PS2X_lib.hライブラリを使用するだけで済みました。コードの先頭に追加されています。
#include
Hブリッジに接続されたArduinoのピンを定義します。私が使用したのと同じconnectiosを使用する場合、次の構成になります。別のピンを使用する場合は、コードのこの部分を更新してください。
//これらはブリッジドライバーの方向を設定するために使用されます。 #define ENA 3 // ENA #define MOTORA_1 4 // IN3 #define MOTORA_2 5 // IN4 #define MOTORB_1 8 // IN1 #define MOTORB_2 7 // IN2 #define ENB 6 // ENB
一部のグローバル変数は、セットアップの前に宣言されました( p2sx 、エラー 、タイプ およびバイブレーション )。 1つ目は、PS2Xクラスのインスタンスです。接続中のエラーステータスはエラーに保存されます 整数。 タイプ およびバイブレーション コントローラーのタイプ(DualShockまたはGuitarHeroコントローラー)と、特定のコマンドで振動するかどうかを示します。
セットアップ中に最初に行ったのは、I / Oピンの状態を(出力として)構成し、イネーブルピンをLOWに設定することでした。このようにして、起動時に両方のモーターを無効にし、残りのコードを待機している間、ロボットがランダムに移動することはありません。
//出力ピンを構成しますpinMode(ENA、OUTPUT); pinMode(MOTORA_1、OUTPUT); pinMode(MOTORA_2、OUTPUT); pinMode(ENB、OUTPUT); pinMode(MOTORB_1、OUTPUT); pinMode(MOTORB_2、OUTPUT); //両方のモーターを無効にしますdigitalWrite(ENA、0); digitalWrite(ENB、0);
次に、シリアルポート通信を開始しました(コードのデバッグに役立ちます)。適切なボーレートを選択し、シリアルモニターで同じ速度を設定します。
//シリアル通信を開始しますSerial.begin(57600);
最後に、ジョイスティックレシーバーに接続されたArduinoのピン(それぞれ時計、コマンド、注意、データ)を使用してps2xオブジェクトを構成します。エラーが返される場合があります(シリアルモニターに表示されます)。コントローラーのタイプも表示されなくなります(ただし、この時点で手元にあるコントローラーのタイプはすでにわかっているはずです:D)。
error =ps2x.config_gamepad(13,11,10,12、true、true); //ピンと設定を設定します:GamePad(clock、command、attention、data、Pressures?、Rumble?)エラーをチェックします//エラーをチェックしますif(error ==0){Serial.println( "Found Controller、configuredsuccessful" ); } else if(error ==1)Serial.println( "コントローラーが見つかりません。配線を確認するか、Arduinoをリセットしてください"); else if(error ==2)Serial.println( "コントローラーが見つかりましたが、コマンドを受け入れていません"); else if(error ==3)Serial.println( "コントローラーが圧力モードへの移行を拒否しているため、サポートされていない可能性があります。"); //コントローラのタイプを確認しますtype =ps2x.readType(); switch(type){case 0:Serial.println( "Unknown Controller type");壊す;ケース1:Serial.println( "DualShock Controller Found");壊す;ケース2:Serial.println( "GuitarHero Controller Found");壊す; }
メインループ中に、Arduinoは各D-padボタン(UP、DOWN、LEFT、RIGTH)を読み取り、ホイールを動かすために出力ピンに異なる値を設定します。少し遅れて、新しいループが開始されます。
次のセクションでは、UPボタンが押された場合にロボットを前方に移動する方法を示します。 MOTORA_1ピンとMOTORA_2ピンは、モーターAの回転方向を定義します。ENAは、移動が有効かどうか(モーターのオン/オフ)を定義します。これは「アナログ」出力(実際にはPWM出力)であることに注意してください。この値は0から1023の間の値である必要があります。これにより、PWMが変調され、hブリッジの出力の平均電圧が変化します(0から12Vの間)。平均電圧が低すぎると、モーターはまったく動きません。
// MOVE FORWARD if(ps2x.Button(PSB_PAD_UP)){digitalWrite(MOTORA_1、LOW); digitalWrite(MOTORA_2、HIGH); digitalWrite(MOTORB_1、HIGH); digitalWrite(MOTORB_2、LOW); analogWrite(ENB、1023); analogWrite(ENA、1023); Serial.println( "前進"); }
* ENAピンとENBピンにはPWM出力を使用しました。このように、1023は最大の長さ(ピンは常にオン)のパルスを表し、0はパルスがない(ピンは常にオフ)ことを表します。ここで別の(小さい)値を使用すると、端子の平均電圧が小さくなるため、モーターの動作が遅くなると予想されます。
ステップ7:スケッチ#2-アナログスティックとデジタルボタン(L2とR2)
ある時点で、すべてのコンソールは2本のアナログスティックを備えたジョイスティックを採用していました。これらの新しい入力により、力に敏感な入力が可能になり、可変速度のアクションが作成され、あらゆる種類のビデオゲームで人気が高まりました。
この2番目の例では、タンクを操縦するためのアナログスイッチと、スロットルおよびブレーキ/リバースとしてのプッシュボタンのペアを使用したいと思いました。この種の構成は、たとえばマリオカートなどの多くのレーシングゲームで非常に人気があります。 R2ボタンを押してタンクを加速し、L2を押して後進し、左スティックのx位置に基づいて移動方向を設定します。
私が使ったロボットキットの種類は慣性があまりありません(モーターの電圧が0Vに設定されていると、しばらく動き続けません)。このように、ロボットにブレーキをかけるためのコマンドを定義する必要はありませんでした。
ほとんどのコードは前のステップですでに説明されています。 1つの違いは、各モーターの速度(0〜1023)を格納する2つの変数を定義したことです。
int motor_right_speed =0;
int motor_left_speed =0;
メインループでは、Arduinoは左スティックのx位置を読み取ります。 0〜255の値を受け取り、-1023〜1023の間にマップします。
この値は、各トラックの速度に差を生じさせ、ロボットを左または右に回転させるために、各モーターの速度に加算(または減算)されます。
int nJoyL =ps2x.Analog(PSS_LX); //左スティックを読み取りますnJoyL =map(nJoyL、0、255、1023、-1023); motor_right_speed =1023; motor_left_speed =1023; if(nJoyL <0){motor_right_speed =motor_right_speed + nJoyL; } if(nJoyL> 0){motor_left_speed =motor_left_speed --nJoyL; }
R2ボタンを押すと、タンクが前進します。このようにして、Arduinoはモーターピンに適切な値を設定します。 ENAとENBは、各モーターに必要な速度に比例した値で、各モーターへの「アナログ」出力を作成します(左スティックのx位置に基づく)。
L2も同様のことをしますが、モーターの方向を逆にします。
if(ps2x.Button(PSB_R2)){digitalWrite(MOTORA_1、LOW); digitalWrite(MOTORA_2、HIGH); digitalWrite(MOTORB_1、HIGH); digitalWrite(MOTORB_2、LOW); analogWrite(ENA、motor_right_speed); analogWrite(ENB、motor_left_speed); } if(ps2x.Button(PSB_L2)){digitalWrite(MOTORA_1、HIGH); digitalWrite(MOTORA_2、LOW); digitalWrite(MOTORB_1、LOW); digitalWrite(MOTORB_2、HIGH); analogWrite(ENA、motor_right_speed); analogWrite(ENB、motor_left_speed); } if(!ps2x.Button(PSB_L2)&&!ps2x.Button(PSB_R2)){analogWrite(ENA、0); analogWrite(ENB、0); }
どのボタンも押されなかった場合、モーターは無効になります。
ステップ8:スケッチ#3-左右のアナログスティック(差動ドライブ)
これは、タンクを制御するための私のお気に入りの方法です(ただし、リソースの点では最適ではありません)。まるで本物の大きな機械を両手で操作しているような気分にさせてくれます!
このコードでは、両方のスティックを使用して、各トラックの方向と速度を設定しました。左スティックは左トラックを制御し、右スティックは右トラックを制御します。
コードは前に説明したものとほとんど同じです。しかし、今回は両方のスティックのy位置を読みたかった:
int nJoyL =ps2x.Analog(PSS_LY); //左スティックを読み取りますintnJoyR =ps2x.Analog(PSS_RY); //右スティックを読み取りますnJoyL =map(nJoyL、0、255、1023、-1023); nJoyR =map(nJoyR、0、255、-1023、1023);
スティックの位置に応じて、コードは各モーターの方向を設定するためにデジタルピンを設定します。
イネーブル(1023)で固定値を使用しましたが、アナログスティックの実際の値に基づいて可変値を使用します。マイクロコントローラーがモーターを無効にするデッドバンド(+ -50)を定義しました。
//両方のアナログスティックに基づいて移動を実行if(nJoyR> 50){digitalWrite(MOTORA_1、HIGH); digitalWrite(MOTORA_2、LOW); analogWrite(ENA、1023); } if(nJoyR <-50){digitalWrite(MOTORA_1、LOW); digitalWrite(MOTORA_2、HIGH); analogWrite(ENA、1023); } if(abs(nJoyR)<50){analogWrite(ENA、0); }
ステップ9:スケッチ#4-左アナログスティックのみ
この最後のSketchアプリでは、1つのジョイスティックを使用してロボットを制御しました。リソースの使用に関しては最適です(さまざまなアクションを構成するためのボタンがたくさん残っています)が、理解するのは非常に困難です。
各トラックの速度は、ジョイスティックのx位置とy位置に応じて定義されます。このようにして、各トラックに異なる速度を適用し、異なる速度/方向でロボットを動かすことができます。ここで使用されているコードは、次のチュートリアルから派生したものです。ぜひチェックしてください!
https://www.impulseadventure.com/elec/robot-differential-steering.html
ステップ10:最終的な考慮事項
私はこのプロジェクトに多大な努力を払い、可能な限り明確で教育的なものにするよう努めました。あなたがそれを好きなら、それを「好き」と「共有」することを忘れないでください。あなたのサポートは私にとって非常に重要です! :D
それでも私のチュートリアルに従わない場合は、ロボット工学に関する他のチュートリアルをご覧ください。気に入っていただければ幸いです!
https://www.hackster.io/igorF2/joy-robot-robo-da-alegria-bba54f
https://www.hackster.io/igorF2/widc-wi-fi-driven-fpv-robot-8f1e09
https://www.hackster.io/igorF2/nunchuk-managed-robotic-arm-with-arduino-b1c0fa
https://www.hackster.io/igorF2/wi-fi-browser-managed-robotic-arm-89b63d
少額のビットコイン寄付で私の将来のプロジェクトをサポートすることを検討してください! :D
BTCデポジットアドレス:1FiWFYSjRaL7sLdr5wr6h86QkMA6pQxkXJ
コード
- スケッチ#1
- スケッチ#2
- スケッチ#3
- スケッチ#4
スケッチ#1 Arduino
// IgorFonsecaによるPS2タンク@ 2019 // PS2ジョイスティックを使用して、十字キーボタンを使用してロボットタンクを制御します// Bill Porter2011によるPS2Xライブラリを使用した例に基づいています//上記のすべてのテキストを含める必要があります// include libraries#include//これらは、ブリッジドライバーの方向を設定するために使用されます。#define ENA 3 // ENA#define MOTORA_1 4 // IN3#define MOTORA_2 5 // IN4 #define MOTORB_1 8 // IN1#define MOTORB_2 7 // IN2#define ENB 6 // ENBPS2X ps2x; // PS2コントローラークラスを作成します//現在、ライブラリはホットプラグ対応コントローラーをサポートしていません。つまり、//コントローラーを接続した後にArduinoを再起動するか、//コントローラーを接続した後にconfig_gamepad(pins)を再度呼び出す必要があります。 intエラー=0; byte type =0; byte vibrate =0; void setup(){//出力ピンを構成しますpinMode(ENA、OUTPUT); pinMode(MOTORA_1、OUTPUT); pinMode(MOTORA_2、OUTPUT); pinMode(ENB、OUTPUT); pinMode(MOTORB_1、OUTPUT); pinMode(MOTORB_2、OUTPUT); //両方のモーターを無効にしますdigitalWrite(ENA、0); digitalWrite(ENB、0); //シリアル通信を開始しますSerial.begin(57600);エラー=ps2x.config_gamepad(13,11,10,12、true、true); //ピンと設定を設定します:GamePad(clock、command、attention、data、Pressures?、Rumble?)エラーをチェックします//エラーをチェックしますif(error ==0){Serial.println( "Found Controller、configuredsuccessful" ); } else if(error ==1)Serial.println( "コントローラーが見つかりません。配線を確認するか、Arduinoをリセットしてください"); else if(error ==2)Serial.println( "コントローラーが見つかりましたが、コマンドを受け入れていません"); else if(error ==3)Serial.println( "コントローラーが圧力モードへの移行を拒否しているため、サポートされていない可能性があります。"); //コントローラのタイプを確認しますtype =ps2x.readType(); switch(type){case 0:Serial.println( "Unknown Controller type");壊す; case 1:Serial.println("DualShock Controller Found");壊す; case 2:Serial.println("GuitarHero Controller Found");壊す; }}// Main loopvoid loop(){ if(error ==1) //skip loop if no controller found return; else { //DualShock Controller ps2x.read_gamepad(false, vibrate); // disable vibration of the controller // Perform movements based on D-pad buttons // MOVE FORWARD if(ps2x.Button(PSB_PAD_UP)) { digitalWrite(MOTORA_1,LOW); digitalWrite(MOTORA_2,HIGH); digitalWrite(MOTORB_1,HIGH); digitalWrite(MOTORB_2,LOW); analogWrite(ENB, 1023); analogWrite(ENA, 1023); Serial.println("Move forward"); } // TURN RIGHT if(ps2x.Button(PSB_PAD_RIGHT)){ digitalWrite(MOTORA_1,HIGH); digitalWrite(MOTORA_2,LOW); digitalWrite(MOTORB_1,HIGH); digitalWrite(MOTORB_2,LOW); analogWrite(ENB, 1023); analogWrite(ENA, 1023); Serial.println("Turn right"); } // TURN LEFT if(ps2x.Button(PSB_PAD_LEFT)){ digitalWrite(MOTORA_1,LOW); digitalWrite(MOTORA_2,HIGH); digitalWrite(MOTORB_1,LOW); digitalWrite(MOTORB_2,HIGH); analogWrite(ENB, 1023); analogWrite(ENA, 1023); Serial.println("Turn left"); } // MOVE BACK if(ps2x.Button(PSB_PAD_DOWN)){ digitalWrite(MOTORA_1,HIGH); digitalWrite(MOTORA_2,LOW); digitalWrite(MOTORB_1,LOW); digitalWrite(MOTORB_2,HIGH); analogWrite(ENB, 1023); analogWrite(ENA, 1023); Serial.println("Move back"); } if (!ps2x.Button(PSB_PAD_DOWN) &&!ps2x.Button(PSB_PAD_UP) &&!ps2x.Button(PSB_PAD_RIGHT) &&!ps2x.Button(PSB_PAD_LEFT)) { analogWrite(ENB, 0); analogWrite(ENA, 0); } delay(50); }}
Sketch #2Arduino
// PS2 Tank by Igor Fonseca @2019// Controls a robotic tank using a PS2 joystick, using D-pad buttons// based on an example using the PS2X library by Bill Porter 2011// All text above must be included in any redistribution.// include libraries#include// These are used to set the direction of the bridge driver.#define ENA 3 //ENA#define MOTORA_1 4 //IN3#define MOTORA_2 5 //IN4#define MOTORB_1 8 //IN1#define MOTORB_2 7 //IN2#define ENB 6 //ENBint motor_right_speed =0;int motor_left_speed =0;PS2X ps2x; // create PS2 Controller Class//right now, the library does NOT support hot pluggable controllers, meaning //you must always either restart your Arduino after you conect the controller, //or call config_gamepad(pins) again after connecting the controller.int error =0; byte type =0;byte vibrate =0;void setup(){ // Configure output pins pinMode(ENA, OUTPUT); pinMode(MOTORA_1, OUTPUT); pinMode(MOTORA_2, OUTPUT); pinMode(ENB, OUTPUT); pinMode(MOTORB_1, OUTPUT); pinMode(MOTORB_2, OUTPUT); // Disable both motors digitalWrite(ENA,0); digitalWrite(ENB,0); // Start serial communication Serial.begin(57600); error =ps2x.config_gamepad(13,11,10,12, true, true); //setup pins and settings:GamePad(clock, command, attention, data, Pressures?, Rumble?) check for error // Check for error if(error ==0){ Serial.println("Found Controller, configured successful"); } else if(error ==1) Serial.println("No controller found, check wiring or reset the Arduino"); else if(error ==2) Serial.println("Controller found but not accepting commands"); else if(error ==3) Serial.println("Controller refusing to enter Pressures mode, may not support it."); // Check for the type of controller type =ps2x.readType(); switch(type) { case 0:Serial.println("Unknown Controller type");壊す; case 1:Serial.println("DualShock Controller Found");壊す; case 2:Serial.println("GuitarHero Controller Found");壊す; }}// Main loopvoid loop(){ if(error ==1) //skip loop if no controller found return; else { //DualShock Controller ps2x.read_gamepad(false, vibrate); // disable vibration of the controller int nJoyL =ps2x.Analog(PSS_LX); // read left stick nJoyL =map(nJoyL, 0, 255, 1023, -1023); int motor_right_speed =1023; int motor_left_speed =1023; if (nJoyL <0) { motor_right_speed =motor_right_speed + nJoyL; } if (nJoyL> 0) { motor_left_speed =motor_left_speed - nJoyL; } if(ps2x.Button(PSB_R2)) { digitalWrite(MOTORA_1,LOW); digitalWrite(MOTORA_2,HIGH); digitalWrite(MOTORB_1,HIGH); digitalWrite(MOTORB_2,LOW); analogWrite(ENA, motor_right_speed); analogWrite(ENB, motor_left_speed); } if(ps2x.Button(PSB_L2)) { digitalWrite(MOTORA_1,HIGH); digitalWrite(MOTORA_2,LOW); digitalWrite(MOTORB_1,LOW); digitalWrite(MOTORB_2,HIGH); analogWrite(ENA, motor_right_speed); analogWrite(ENB, motor_left_speed); } if(!ps2x.Button(PSB_L2) &&!ps2x.Button(PSB_R2)) { analogWrite(ENA, 0); analogWrite(ENB, 0); } delay(50); }}
Sketch #3Arduino
// PS2 Tank by Igor Fonseca @2019// Controls a robotic tank using a PS2 joystick, using D-pad buttons// based on an example using the PS2X library by Bill Porter 2011// All text above must be included in any redistribution.// include libraries#include// These are used to set the direction of the bridge driver.#define ENA 3 //ENA#define MOTORA_1 4 //IN3#define MOTORA_2 5 //IN4#define MOTORB_1 8 //IN1#define MOTORB_2 7 //IN2#define ENB 6 //ENBPS2X ps2x; // create PS2 Controller Class//right now, the library does NOT support hot pluggable controllers, meaning //you must always either restart your Arduino after you conect the controller, //or call config_gamepad(pins) again after connecting the controller.int error =0; byte type =0;byte vibrate =0;void setup(){ // Configure output pins pinMode(ENA, OUTPUT); pinMode(MOTORA_1, OUTPUT); pinMode(MOTORA_2, OUTPUT); pinMode(ENB, OUTPUT); pinMode(MOTORB_1, OUTPUT); pinMode(MOTORB_2, OUTPUT); // Disable both motors digitalWrite(ENA,0); digitalWrite(ENB,0); // Start serial communication Serial.begin(57600); error =ps2x.config_gamepad(13,11,10,12, true, true); //setup pins and settings:GamePad(clock, command, attention, data, Pressures?, Rumble?) check for error // Check for error if(error ==0){ Serial.println("Found Controller, configured successful"); } else if(error ==1) Serial.println("No controller found, check wiring or reset the Arduino"); else if(error ==2) Serial.println("Controller found but not accepting commands"); else if(error ==3) Serial.println("Controller refusing to enter Pressures mode, may not support it."); // Check for the type of controller type =ps2x.readType(); switch(type) { case 0:Serial.println("Unknown Controller type");壊す; case 1:Serial.println("DualShock Controller Found");壊す; case 2:Serial.println("GuitarHero Controller Found");壊す; }}// Main loopvoid loop(){ if(error ==1) //skip loop if no controller found return; else { //DualShock Controller ps2x.read_gamepad(false, vibrate); // disable vibration of the controller int nJoyL =ps2x.Analog(PSS_LY); // read left stick int nJoyR =ps2x.Analog(PSS_RY); // read right stick nJoyL =map(nJoyL, 0, 255, 1023, -1023); nJoyR =map(nJoyR, 0, 255, -1023, 1023); // Perform movements based on both analog sticks if(nJoyR>50) { digitalWrite(MOTORA_1,HIGH); digitalWrite(MOTORA_2,LOW); analogWrite(ENA, 1023); } if(nJoyR<-50) { digitalWrite(MOTORA_1,LOW); digitalWrite(MOTORA_2,HIGH); analogWrite(ENA, 1023); } if (abs(nJoyR)<50) { analogWrite(ENA, 0); } if(nJoyL>50) { digitalWrite(MOTORB_1,HIGH); digitalWrite(MOTORB_2,LOW); analogWrite(ENB, 1023); } if(nJoyL<-50) { digitalWrite(MOTORB_1,LOW); digitalWrite(MOTORB_2,HIGH); analogWrite(ENB, 1023); } if (abs(nJoyL)<50) { analogWrite(ENB, 0); } delay(50); }}
Sketch #4Arduino
// PS2 Tank by Igor Fonseca @2019// Controls a robotic tank using a PS2 joystick, using left analog stick// based on an example using the PS2X library by Bill Porter 2011// All text above must be included in any redistribution.// include libraries#include//for v1.6// These are used to set the direction of the bridge driver.#define ENA 3 //ENA#define MOTORA_1 4 //IN3#define MOTORA_2 5 //IN4#define MOTORB_1 8 //IN1#define MOTORB_2 7 //IN2#define ENB 6 //ENBint motor_right_speed =0;int motor_left_speed =0;PS2X ps2x; // create PS2 Controller Class//right now, the library does NOT support hot pluggable controllers, meaning //you must always either restart your Arduino after you conect the controller, //or call config_gamepad(pins) again after connecting the controller.int error =0; byte type =0;byte vibrate =0;void setup(){ // Configure output pins pinMode(ENA, OUTPUT); pinMode(MOTORA_1, OUTPUT); pinMode(MOTORA_2, OUTPUT); pinMode(ENB, OUTPUT); pinMode(MOTORB_1, OUTPUT); pinMode(MOTORB_2, OUTPUT); // Disable both motors digitalWrite(ENA,0); digitalWrite(ENB,0); // Start serial communication Serial.begin(57600); error =ps2x.config_gamepad(13,11,10,12, true, true); //setup pins and settings:GamePad(clock, command, attention, data, Pressures?, Rumble?) check for error // Check for error if(error ==0){ Serial.println("Found Controller, configured successful"); } else if(error ==1) Serial.println("No controller found, check wiring or reset the Arduino"); else if(error ==2) Serial.println("Controller found but not accepting commands"); else if(error ==3) Serial.println("Controller refusing to enter Pressures mode, may not support it."); // Check for the type of controller type =ps2x.readType(); switch(type) { case 0:Serial.println("Unknown Controller type");壊す; case 1:Serial.println("DualShock Controller Found");壊す; case 2:Serial.println("GuitarHero Controller Found");壊す; }}// Main loopvoid loop(){ if(error ==1) //skip loop if no controller found return; else { //DualShock Controller ps2x.read_gamepad(false, vibrate); // disable vibration of the controller int nJoyX =ps2x.Analog(PSS_LX); // read x-joystick int nJoyY =ps2x.Analog(PSS_LY); // read y-joystick nJoyX =map(nJoyX, 0, 255, -1023, 1023); nJoyY =map(nJoyY, 0, 255, 1023, -1023); // OUTPUTS int nMotMixL; // Motor (left) mixed output int nMotMixR; // Motor (right) mixed output // CONFIG // - fPivYLimt :The threshold at which the pivot action starts // This threshold is measured in units on the Y-axis // away from the X-axis (Y=0). A greater value will assign // more of the joystick's range to pivot actions. // Allowable range:(0..+127) float fPivYLimit =1023.0; // TEMP VARIABLES float nMotPremixL; // Motor (left) premixed output float nMotPremixR; // Motor (right) premixed output int nPivSpeed; // Pivot Speed float fPivScale; // Balance scale between drive and pivot // Calculate Drive Turn output due to Joystick X input if (nJoyY>=0) { // Forward nMotPremixL =(nJoyX>=0)? 1023.0 :(1023.0 + nJoyX); nMotPremixR =(nJoyX>=0)? (1023.0 - nJoyX) :1023.0; } else { // Reverse nMotPremixL =(nJoyX>=0)? (1023.0 - nJoyX) :1023.0; nMotPremixR =(nJoyX>=0)? 1023.0 :(1023.0 + nJoyX); } // Scale Drive output due to Joystick Y input (throttle) nMotPremixL =nMotPremixL * nJoyY/1023.0; nMotPremixR =nMotPremixR * nJoyY/1023.0; // Now calculate pivot amount // - Strength of pivot (nPivSpeed) based on Joystick X input // - Blending of pivot vs drive (fPivScale) based on Joystick Y input nPivSpeed =nJoyX; fPivScale =(abs(nJoyY)>fPivYLimit)? 0.0 :(1.0 - abs(nJoyY)/fPivYLimit); // Calculate final mix of Drive and Pivot nMotMixL =(1.0-fPivScale)*nMotPremixL + fPivScale*( nPivSpeed); nMotMixR =(1.0-fPivScale)*nMotPremixR + fPivScale*(-nPivSpeed); motor_left_speed =nMotMixL; motor_right_speed =nMotMixR; if (motor_right_speed> 50) { digitalWrite(MOTORB_1,HIGH); digitalWrite(MOTORB_2,LOW); } else if (motor_right_speed <-50) { digitalWrite(MOTORB_1,LOW); digitalWrite(MOTORB_2, HIGH); } else { digitalWrite(MOTORB_1, LOW); digitalWrite(MOTORB_2, LOW); } if (motor_left_speed> 50) { digitalWrite(MOTORA_1, LOW); digitalWrite(MOTORA_2, HIGH); } else if (motor_left_speed <-50) { digitalWrite(MOTORA_1,HIGH); digitalWrite(MOTORA_2,LOW); } else { digitalWrite(MOTORA_1, LOW); digitalWrite(MOTORA_2, LOW); } analogWrite(ENA, abs(motor_left_speed)); analogWrite(ENB, abs(motor_right_speed)); if (abs(motor_left_speed> 50) || abs(motor_left_speed> 50)) { Serial.println("Moving!"); } delay(50); }}
回路図
製造プロセス
- ArduinoとRaspberryPiを使用してインターネット制御のビデオストリーミングロボットを構築する
- Unopad-Abletonを搭載したArduinoMIDIコントローラー
- サーボモーター付きロボット回避障害物
- ArduinoとAndroidデバイスでルンバロボットを制御する
- Nunchuk制御ロボットアーム(Arduino付き)
- Arduino Nano:ジョイスティックで2つのステッピングモーターを制御
- Arduinoジョイスティック
- PS2コントローラーで制御されるバトルボットを構築する
- AndroidアプリでArduinoロボットアームを制御する
- ArduinoNanoで食べるロボットを作る|金ネジ
- Dabbleを使用して制御されたArduinoで作られた4輪ロボット