ESP8266とMilkcocoaでハードウエアをリモート操作できるようにする

ハードウエアを遠隔操作できるようにするのは、Milkcocoaを使えば簡単にできます！荒削りなので変更お待ちしております。

#必要となるもの
ESP8266（日本ではESP-WROOM-02）
インターネット接続
MilkcocoaのAPPID
#できること
- pinMode
- pinPullup
- digitalRead
- digitalWrite
- analogRead
- analogWrite
- uartMode
- uartWrite
- uartRead
- Reset
- Sleep


#プログラムの解説
こちらのプログラムは、Nefryで使うことをベースに考えられているので、Wifi接続などがありません。Nefry以外のESP8266で使う場合はWifi接続するプログラムをコメントアウトしてください。
プログラムのAPP_IDにご自身のIDを入力することで使うことが可能になります！
Milkcocoaにデータを送信する部分はご自身でつくってみてください。（私がWeb側が強くないので…）

##MilkcocoaからESP8266へデータを送るとき
pin,mode,stateを送信してください。
##ESP8266からMilkcocoaへデータを送るとき
Milkcocoaからのデータが実行されたとき、0が返され、ESP8266からデータ取った時にはそのデータも付属します。

```cpp:arduino.ino
#include <Milkcocoa.h>
#include <ESP8266WiFi.h>
/************************* Your Milkcocoa Setup *********************************/
#define MILKCOCOA_APP_ID      ""
#define MILKCOCOA_DATASTORE   "arduino"
#define MILKCOCOA_DATASTORE_SEND   "arduino_send"

#define MILKCOCOA_SERVERPORT  1883
WiFiClient client;
const char MQTT_SERVER[] PROGMEM    = MILKCOCOA_APP_ID ".mlkcca.com";
const char MQTT_CLIENTID[] PROGMEM  = __TIME__ MILKCOCOA_APP_ID;

Milkcocoa milkcocoa = Milkcocoa(&client, MQTT_SERVER, MILKCOCOA_SERVERPORT, MILKCOCOA_APP_ID, MQTT_CLIENTID);

void setup() {
/*  
  WiFi.begin(WLAN_SSID, WLAN_PASS);
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
*/
  milkcocoa.on(MILKCOCOA_DATASTORE, "push", arduino);
}

void loop() {
  milkcocoa.loop();
}

void arduino(DataElement elem) {
  Serial.println("onpush");
  DataElement Send = DataElement();
  String mode_setting = elem.getString("mode");
  int pin=pins(elem.getString("pin"));
  String state =states(elem.getString("state"));
  Serial.println(mode_setting.toInt());
  switch (mode_setting.toInt()) {
      int send_data;
    case 1: //pinMode
      pinMode(pin,state.toInt()); //state INPUT or OUTPUT
      Send.setValue("return", 0);
      break;
    case 2: //pinPullup
      pinMode(pin, INPUT_PULLUP);
      Send.setValue("return", 0);
      break;
    case 3: //digitalRead
      send_data = digitalRead(pin); //HorL
      Send.setValue("return", 0);
      Send.setValue("send_data", send_data);
      //upload
      break;
    case 4: //digitalWrite
      digitalWrite(pin, state.toInt()); //state HIGH(3.3v)orLOW(0v)
      Send.setValue("return", 0);
      break;
    case 5: //analogRead
      send_data = analogRead(A0); //max1024
      Send.setValue("return", 0);
      Send.setValue("send_data", send_data);
      //upload
      break;
    case 6: //analogWrite(pwm)
      //D2,D3,D4pinのみ有効
      analogWrite(pin, state.toInt()); //state max255(3.3v)~min0(0v)
      Send.setValue("return", 0);
      break;
    case 7: //uartMode(Baudrate)
      Serial.begin(state.toInt());//9600,14400,19200,28800,38400,57600,115200の中から選択
      Send.setValue("return", 0);
      break;
    case 8: //uartWrite
      Serial.print(state);
      Send.setValue("return", 0);
      break;
    case 9: //uartRead
      Serial.println("uartread");
      char read_char[128], i, w;
      i = 0;
      w = 0;
      while (Serial.available() <= 0 || w != 10) {
        Serial.println("check");
        while (Serial.available() > 0) {
          Serial.println("char get!");
          read_char[i] = Serial.read();
          if (i > 127 || read_char[i] == '\n' || read_char[i] == '\r') {
            read_char[i - 1] = '\0';
            Serial.write(read_char);
            Serial.write("\n");
            break;
          }
          i++;
        }
        if (i != 0)break;
        delay(500);
      }
      Send.setValue("return", 0);
      Send.setValue("send_data", read_char);
      //upload
      break;
    case 10: //reset
      Send.setValue("return", 0);
      Send.setValue("mode_setting", elem.getString("mode"));
      milkcocoa.push(MILKCOCOA_DATASTORE_SEND, Send);
      delay(1000);
      ESP.restart();
      break;
    case 11: //sleep
      Send.setValue("return", 0);
      Send.setValue("mode_setting",elem.getString("mode"));
      milkcocoa.push(MILKCOCOA_DATASTORE_SEND, Send);
      delay(1000);
      ESP.deepSleep(state.toInt() * 1000 * 1000 , WAKE_RF_DEFAULT);
      delay(1000);
      break;
    case 12: //i2cMode
      //Wire.begin();
      break;
    case 13: //i2cWrite
      break;
    case 14: //i2cRead
      break;
    case 15:
      break;
    case 16:
      break;
    case 17:
      break;
    //
    default:
      Send.setValue("return", 1);
      break;
  }
  Send.setValue("mode_setting", elem.getString("mode"));
  milkcocoa.push(MILKCOCOA_DATASTORE_SEND, Send);
  Serial.println("Send");
}
int pins(String pinS){
  int pin;
if(pinS.toInt()==0){
    pin=D0;
  }else if(pinS.toInt()==1){
    pin=D1;
  }else if(pinS.toInt()==2){
    pin=D2;
  }else if(pinS.toInt()==3){
    pin=D3;
  }else if(pinS.toInt()==4){
    pin=D4;
  }else if(pinS.toInt()==5){
    pin=D5;
  }
return pin;
}
String states(String stateS){
  String state;
if(stateS.compareTo("high")==0){
    state="1";
  }else if(stateS.compareTo("HIGH")==0){
    state="1";
  }else if(stateS.compareTo("low")==0){
    state="0";
  }else if(stateS.compareTo("LOW")==0){
    state="0";
  }else if(stateS.compareTo("OUTPUT")==0){
    state="1";
  }else if(stateS.compareTo("output")==0){
    state="1";
  }else if(stateS.compareTo("INPUT ")==0){
    state="0";
  }else if(stateS.compareTo("input")==0){
    state="0";
  }else{
    state=stateS;
  }
return state;
}
```

#デモ
LEDをWebページから操作するデモになります。
[![ハードウエアをリモート操作するデモになります](http://img.youtube.com/vi/DRLvA3r7zU4/0.jpg)](https://youtu.be/DRLvA3r7zU4)