ESP32のテストを行う
室内の中の何かとマイコンを通信させたい場合、WifiやBluetoothで通信できるととても便利ですよね。
WifiやBLEで通信できるマイコンにも興味が出てきたので、部品棚のESP32-DevkitCでテストしてみることにしました。
ESP32のGPIOは+3.3Vなので意外とすぐ動いてしまったりするかも?ということで、Brook UFB経由でPS3のゲームを操作することを目標にします。
また直配線するだけでは面白くないため、Wifiの確認も含めてスマホから操作するというチャレンジをしてみます。
※今回はたまたまPS3をターゲットにしましたが、他のゲーム機やPCでも同じように操作可能だと思います。
ESP32について
ESP32はWifi(2.4GHz帯)やBLE(Bluetooth Low Energy)を使用できる低価格で性能の良いマイコンです。
最近ではM5Stackシリーズで使用されていることで有名ですね。
ESP32については参考になるサイトがたくさんありますので一部を掲載させていただきます。
参考
ESP32入門 通信機能が標準搭載されたマイコン・ボード (1) 準備作りながら学ぶArduino+=電子工作入門
参考
esp32-wroomDevkitCをarduino IDEでセットアップからサーボ駆動まで(Windows)Qiita @WK_ZAKKさん
ESP32-Devkitcではプログラムの書き込みに失敗することがあるようですので、その場合は下記を参考にコンデンサーを付けると改善できるようです。
うちでもEN-GND間に0.1μFを付けています。
参考
ESP32のプログラム書込みを安定させるQiita @h_nariさん
テストの流れ
以下の流れで進めていくことにしました。
- 何らかのプログラムを書き込めること
- Blynkで画面をレイアウト
- ArduinoIDEでプログラム作成
- Blynkからレバー・ボタンを想定したLED操作
- LEDの代わりにUFB J9コネクタに接続しテスト
ESP32は初めてなので、GPIO1つだけを使用してまずはLチカで基本的な確認をします。
ひとまず操作するのに必要最低限のWidgetだけを配置。
Blynkのサンプルを参考にしつつ作成します。
プログラムで指定したGPIOが想定通り操作できていることを確認します。
負論理で動かす前提なので、点灯しているLEDがボタンを押すことで消灯すること。
実際にPS3に接続してテストします。
作ってみる
効率的にスマホから操作できるようにするためにBlynkアプリを使用しましょう。
Android/iPhoneで利用可能です。
Blynkで画面レイアウトを作成する
具体的なセットアップ方法などについては下記サイトが参考になると思います。
参考
ESP32を遠隔操作!Blynkの使い方とLチカwak-tech
マイコンの選択
Androidに入れたBlynkアプリを起動し、ESP32 Dev Boardを選択。
CONNECTION TYPE
CONNECTION TYPEでWi-Fiを選択。
Widgetの配置
Widgetを配置する際にはコストがかかります。
無料分のコストを使い切ってしまった場合は、課金して増やす必要があります。
今回は最低限のレバー・ボタンを配置しました。
(画面をスクロールさせたり、タブ切替も可能です)
ボタンの設定
直接GPIOのLOW/HIGHを切り替えることも可能ですが、負論理にしたかったため、VirtualPinを指定しました。
実際のGPIOピンだけでなくVirtualPinを指定できるところがBlynkの優れたところです。
※VirtualPin(実際にあるわけではない仮想的なピン)
レバーの設定
JoyStick Widgetの初期値では0-255の値を取るようになっています。
今回はアナログレバーである必要はないので、扱いやすいように値をもっと少なくします。
当初はx/yともに-1~1(N:0)の値を取るようにしていたのですが、Arduino言語(C/C++ベース)のSwitch case文では-1を扱えないようでしたので、0~2(N:1)としました。
※N:ニュートラル
スケッチ(プログラム)を書く
ソースコードは長くなるので一番下に載せています。
Virtualピンの値によってGPIOのLOW/HIGHを切り替えているだけの単純なものです。
Blinkアプリでプロジェクトを作成した際にauth tokenがメールされてきているはずです。
Wifiのssid/passphraseと併せて忘れずにコーディングしましょう。
スマホアプリ側とのやり取りをプログラムしなくとも、auth tokenを指定するだけで簡単に接続でき非常に便利です。
配線する
テストということもあってただつなぐだけです。
ESP32からUFB-BOX内のUFB J9コネクタに配線します。
- MicroUSBポート
- 5V/GNDピン
- 3.3V/GNDピン
参考
ESP32-DevKitC V4 Getting Started Guidedocs.espressif.com
※「Power Supply Options」参照
アケコンやUFB-BOXに内蔵させたい場合はUFB J9コネクタからVcc(+5V)/GNDを取るのが良いと思います。
一方、USBケーブルでPCと接続する場合(シリアルモニターを使う場合など)はMicroUSBポートから給電でしょうか。
その場合、GNDレベルを合わせるためにUFB J9コネクタのGNDとESP32-DEVkitcのGNDを接続すると良いと思います。(Vccは接続しない)
UFBのネジ端子ブロックからはコントローラーに配線してありますので、今回BlynkのWidgetを配置していないボタンに関してはアケコン側で操作可能です。
ESP32のGPIOには読み取り専用のピンやWifiを使用して際には使えないピンがあったりと、ピン選択に気を付ける必要がありました。
参考
1-3.ESP-WROOM-32(D)sLab工作ガイド
※「(1) デジタル入出力【GPIO 0〜33, GPI 34〜39端子】」参照
動作確認とまとめ
実際に動作確認をしてみたところです。
※ケーブルは充電のために接続しています。
一度Blynkサーバーを経由するため最短の応答速度でも100msと快適にゲームができるほどのレスポンスはありません。正直すごく操作しにくいです。。
しかし今回ESP32・Blinkとも初めて触れたにも関わらず、基本動作確認からPS3をスマホで操作するところまで全体通してわずか2時間程度で済んだ手軽さは大きな魅力です。
- 短期間で作成できる
- 簡単にIoTデバイスが作成できる
- 他の端末でも同時に動作する
Widgetデザイン・Arduinoスケッチ(プログラム)ともに作成工数が大幅に削減できます
今回作成した仕組みもインターネット環境があればどこでも使用できます。
外出先(Wifi圏外)からでもアケコンを操作できるということです。
同じアカウントでログインすれば、他の端末でも同じプロジェクトを同時に開くことができます。
今回は入力操作でしたが、例えばセンサー値の確認やグラフ表示等の場合は効果的に利用できると思います。
Blynkではボタン操作だけでなくもっと様々なことができるようですし、
コマンドコントローラーに関しても、簡単なモード変更やコマンド種別の選択などはスマホで行うと便利かもしれません。
ESP32はAVR系のArduinoよりCPU性能/メモリ量いずれも優れていますし、活用していけばより面白いものが作れそうです。
スケッチ(プログラム)
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 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 | #define BLYNK_PRINT Serial #define P1_Stick_U 16 #define P1_Stick_D 17 #define P1_Stick_L 18 #define P1_Stick_R 19 #define P1_Button_G 21 #define P1_Button_P 22 #define P1_Button_K 23 #define P1_Button_START 4 #include <WiFi.h> #include <WiFiClient.h> #include <BlynkSimpleEsp32.h> volatile int P1_x = 0; volatile int P1_y = 0; volatile int P1_G = 0; volatile int P1_P = 0; volatile int P1_K = 0; volatile int P1_START = 0; //環境に合わせて変更 char auth[] = "xxxxx"; // Blynkのauth token char ssid[] = "xxxxx"; // Wifi(2.4GHz)のssid char pass[] = "xxxxx"; // Wifi(2.4GHz)のpassphrase void setup() { pinMode(P1_Stick_U,OUTPUT); pinMode(P1_Stick_D,OUTPUT); pinMode(P1_Stick_L,OUTPUT); pinMode(P1_Stick_R,OUTPUT); pinMode(P1_Button_G,OUTPUT); pinMode(P1_Button_P,OUTPUT); pinMode(P1_Button_K,OUTPUT); pinMode(P1_Button_START,OUTPUT); // Debug console Serial.begin(115200); Blynk.begin(auth, ssid, pass); } void loop() { Blynk.run(); } BLYNK_WRITE(V1) { P1_G = param.asInt(); if (P1_G == 1){ digitalWrite(P1_Button_G,LOW); } else if (P1_G == 0) { digitalWrite(P1_Button_G,HIGH); } } BLYNK_WRITE(V2) { P1_P = param.asInt(); if (P1_P == 1){ digitalWrite(P1_Button_P,LOW); } else if (P1_P == 0) { digitalWrite(P1_Button_P,HIGH); } } BLYNK_WRITE(V3) { P1_K = param.asInt(); if (P1_K == 1){ digitalWrite(P1_Button_K,LOW); } else if (P1_K == 0) { digitalWrite(P1_Button_K,HIGH); } } BLYNK_WRITE(V4) { P1_START = param.asInt(); if (P1_START == 1){ digitalWrite(P1_Button_START,LOW); } else if (P1_START == 0) { digitalWrite(P1_Button_START,HIGH); } } BLYNK_WRITE(V0) { P1_x = param[0].asInt(); P1_y = param[1].asInt(); // Do something with x and y Serial.print("X = "); Serial.print(P1_x); Serial.print("; Y = "); Serial.println(P1_y); switch (P1_x) { case 0: digitalWrite(P1_Stick_L,LOW); digitalWrite(P1_Stick_R,HIGH); break; case 1: digitalWrite(P1_Stick_L,HIGH); digitalWrite(P1_Stick_R,HIGH); break; case 2: digitalWrite(P1_Stick_L,HIGH); digitalWrite(P1_Stick_R,LOW); break; } switch (P1_y) { case 0: digitalWrite(P1_Stick_U,HIGH); digitalWrite(P1_Stick_D,LOW); break; case 1: digitalWrite(P1_Stick_U,HIGH); digitalWrite(P1_Stick_D,HIGH); break; case 2: digitalWrite(P1_Stick_U,LOW); digitalWrite(P1_Stick_D,HIGH); break; } } |