ESP-WROOM-02用開発環境でスケッチを動かす

wifi経由で操作する電動雲台を軽く作る話だったのが、手軽にwifiが使えるデバイスを使った開発話のようになってしまっているが、行きがかり上続行する。これまで、ESP-WROOM-02に特化した話題として、

という話を続けてきたが、今回は2番目の話の中で作ったハードウェアの上でテスト用のプログラムを動かしてみる。

LEDをチカチカする (ESP_LED0.ino)

#include <Ticker.h>

#define LED1 12
#define LED2 14

Ticker ticker;

long tick_counter = 0;
void ticker_func() {
  tick_counter++;

  if (tick_counter % 50 == 0)
    digitalWrite(LED1, !digitalRead(LED1));
  if (tick_counter % 100 == 0)
    digitalWrite(LED2, !digitalRead(LED2));
}

void setup() {
  Serial.begin(115200);
  
  pinMode(LED1, OUTPUT);
  pinMode(LED2, OUTPUT);
  digitalWrite(LED1, 0);
  digitalWrite(LED2, 0);
  ticker.attach_ms(10, ticker_func);
}
void loop() { }

上記は、WROOM-02のGPIO12とGPIO14に接続した2つのLEDを異なる周期で点滅させるためのスケッチ(ESP_LED0.ino)で、ESP8266に特化したTickerというライブラリを使っている。このライブラリは、指定した周期ごとに指定の関数をコールバックしてくれる。

void setup()内でI/Oピンの設定を行った後で、ticker.attach_ms(10, ticker_func); により10msecごとにticker_func()が呼び出されるよう指定している。
ticker_func()では、変数 tick_counter をインクリメントし、50回ごとにLED1を、100回ごとにLED2をそれぞれ反転している。50回ごとならば0.5秒ごと100回ごとならば1秒ごとにLEDが点滅してくれる。

スケッチの転送

スケッチをWROOM-02に転送する(書き込む)ときには、普通のArduinoボードに書き込むときと同じように、スケッチメニューのマイコンボードに書き込むを選択する。するとスケッチのコンパイルが行われて転送される。

esp8266 スケッチ書込み

転送時には、Uploading xxxxx bytes from … というメッセージに引き続いて 転送中を示す…..(ピリオド) が続々と表示され、通信中を表すためにFT231X用のブレッドボードに載せた赤いLEDが点滅する。転送の完了を表すメッセージが表示されるとよいのだけれど、そういうのがないので、ピリオドの数が増えなくなったら完了。

このとき、事前にGPIO0に接続されているMODEケーブルをPROGRAM側(プルダウン側)に接続してリセットスイッチを押しておき、ESP8266を、UARTダウンロードモード(フラッシュ書込みモード)に変更しておく必要がある。

転送が完了すると、どうやらフラッシュ内に転送されたプログラムが実行されるようで、LEDの点滅が開始する。ただ、このままリセットしてブートすると再びダウンロードモード(書込み待ち)になるので、転送が終わったらMODEケーブルはNORMAL側(プルアップ側)に戻しておいた方がよさそうである。

なお、MODEケーブルがNORMAL側に接続されたままだったり、リセットスイッチを押さずにArduino IDEの「マイコンボードに書き込む」を選択してしまうと転送が失敗し、メッセージ領域に

warning: espcomm_sync failed
error: espcomm_open failed

と表示される。

wifiステーション + httpクライアント

以前はATコマンドでwifi接続とhttp GETを実装したが、今回はESP8266  Communityが用意してくれているライブラリの呼び出しによって同じようなことをやってみる。
….\Arduino15\packages\esp8266\hardware\esp8266\2.0.0\libraries\ESP8266WiFi\examples\WiFiClient\WifiClient.inoを少し手直したのが以下のスケッチ。

/**
 * wifiルーターに接続し、okiraku-camera.tokyoの"/" をGETする。
 */
#include <ESP8266WiFi.h>

static const char* my_ssid     = "#my_ssid#";
static const char* my_password = "#my_password#";
static const char* remote_host = "okiraku-camera.tokyo";

void setup() {
  Serial.begin(115200);
  delay(10);
  Serial.print("\r\nConnecting to router...");
  WiFi.begin(my_ssid, my_password); // wifi ルーターに接続する。
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("connected. WiFi.printDiag()\r\n");
  WiFi.printDiag(Serial);
  Serial.println("");
}

void loop() {
  delay(2000);
  Serial.println("connecting to " + String(remote_host));
  WiFiClient client;
  if (!client.connect(remote_host, 80)) {
    Serial.println("connection failed");
    return;
  }
  client.print("GET /  HTTP/1.1\r\nHost: " + String(remote_host) + "\r\nConnection: close\r\n\r\n");
  delay(10);
  
  // Read all the lines of the reply from server and print them to Serial
  while(client.available()){
    String line = client.readStringUntil('\n');
    Serial.println(line);
  }
  Serial.println();
  Serial.println("closing connection");
  client.stop();
  for(;;) {
    delay(100);
  }
}

このスケッチは、setup()内においてmy_ssidとmy_passwordをssidとパスワード(事前共有キー)としてwifiアクセスポイント(wifiルーター)に接続し、接続できたら WiFi.printDiag()というメソッドを使ってwifiの状態をシリアルモニタに表示する。
次にloop()内で、このブログのドキュメントルート(https://okiraku-camera.tokyo/)にGETリクエストを投げてその応答をシリアルモニタに表示する。機能としてはこれで終わりなので、無限ループに入る。

以下がシリアルモニタに表示された実行結果である(SSIDやPassphraseは書き換えた)。

Connecting to router......connected. WiFi.printDiag()

Mode: STA+AP
PHY mode: N
Channel: 2
AP id: 0
Status: 5
Auto connect: 1
SSID (9): #my_ssid#
Passphrase (13): #my_password#
BSSID set: 0

connecting to okiraku-camera.tokyo
HTTP/1.1 200 OK

Date: Sun, 24 Jan 2016 08:55:05 GMT
Server: Apache
Last-Modified: Sun, 30 Nov 2014 11:55:05 GMT
ETag: "26801a1-52-509122a29d840"
Accept-Ranges: bytes
Content-Length: 82
Connection: close
Content-Type: text/html; charset=UTF-8

<HTML>
<HEAD>
<meta http-equiv="refresh" content="0; url=/blog">
</HEAD>
</HTML>

closing connection

以前ATコマンドでやったときと同じような結果を得ている。ここで気になるのは Auto connect: 1 という行で、素直に受け取ると、次回ブート時から指定のwifiアクセスポイントに自動接続するのかもしれない。

きょうのまとめ

印象としては、ATコマンドでいろいろやるよりすっきり書けるし、wifiアクセスポイントやwebサーバーの実装も用意されているようである。
開発用のハードウェアも一応問題なく動いているし、各種ライブラリの使い方も見えてきた。そろそろATコマンドで実装したのと同程度の操作が可能な雲台の形にしてみようかと思うが、AIR A01用アプリとwifiでの雲台操作の合体にはもう少し時間がかかりそう。