ワイヤレスリモコンを改造しよう6

前回の続き

TinyduinoのWiFi TinyShieldが無事に動くようになったので、JSONを取得してONかOFFかを判定して信号を出すようにしてみた。 JSONをどう読み取ろうか悩んだけど、潔くさぼりにさぼってほぼ判定なし。まあONかOFFだけだし大丈夫でしょう。

WiFi経由でHTTPアクセスする部分はこちらのコードを大いに参考にしました。 Arduino - WiFiWebClientRepeating

というわけで、以下ほぼ全ソースコード。いちぶ伏せています。

#include <SPI.h>
#include <WiFi101.h>

#include "arduino_secrets.h" 
///////please enter your sensitive data in the Secret tab/arduino_secrets.h
char ssid[] = SECRET_SSID;        // your network SSID (name)
char pass[] = SECRET_PASS;    // your network password (use for WPA, or use as key for WEP)
int keyIndex = 0;            // your network key Index number (needed only for WEP)

int status = WL_IDLE_STATUS;

// Initialize the WiFi client library
WiFiClient client;

// server address:
char server[] = "himitsu";

unsigned long lastConnectionTime = 0;            // last time you connected to the server, in milliseconds
const unsigned long postingInterval = 1L * 1000L; // delay between updates, in milliseconds

#define O 4 // control signal output pin
#define SHORT 390 -20 // target - adjustment us
#define LONG  990 -10 // target - adjustment us
#define INTER 9930 -1000 // us
#define NUM 5 // repeat the same command

String inputString = "";         // a String to hold incoming data
bool stringComplete = false;  // whether the string is complete

String on    = "0001010100010101010101110";
String off   = "0001010100010101010101000";

void short_out(){
  digitalWrite(O, HIGH);
  delayMicroseconds(SHORT);
  digitalWrite(O, LOW);
  delayMicroseconds(LONG);
}

void long_out(){
  digitalWrite(O, HIGH);
  delayMicroseconds(LONG);
  digitalWrite(O, LOW);
  delayMicroseconds(SHORT); 
}

void modulate_out(String s){
  int l = s.length();
  //Serial.println(l);
  int i, j;
  short_out();
  for(j=0;j<NUM;j++){
    delayMicroseconds(INTER);
    for(i=0;i<l;i++){
      char c = s.charAt(i);
      if(c == '0'){ short_out(); }
      else{ long_out(); }
    }
  }
}


void setup() {
  //Initialize serial and wait for port to open:
  Serial.begin(115200);
  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }

  pinMode(O, OUTPUT);
  digitalWrite(O, LOW);
  
  WiFi.setPins(8, 2, A3, -1);
  // check for the presence of the shield:
  if (WiFi.status() == WL_NO_SHIELD) {
    Serial.println("WiFi shield not present");
    // don't continue:
    while (true);
  }

  // attempt to connect to WiFi network:
  while ( status != WL_CONNECTED) {
    Serial.print("Attempting to connect to SSID: ");
    Serial.println(ssid);
    // Connect to WPA/WPA2 network. Change this line if using open or WEP network:
    status = WiFi.begin(ssid, pass);

    // wait 10 seconds for connection:
    delay(10000);
  }
  // you're connected now, so print out the status:
  printWiFiStatus();
}

int countDown = 0;
int checkNF = 0;
int lastCommand = 0;
int thisCommand = 0;
void loop() {
  // if there's incoming data from the net connection.
  // send it out the serial port.  This is for debugging
  // purposes only:
  while (client.available()) {
    char c = client.read();
    //Serial.write(c);

    if(checkNF == 1){
      checkNF = 0;
      if(c == 'n'){ // command is on
        thisCommand = 1;
      }
      else if(c == 'f'){  // command is off
        thisCommand = 0;
      }
    }
    if(countDown > 0){
      countDown--;
      if(countDown == 0){
        //Serial.println("check if it is o");
        if(c == 'o'){ checkNF = 1; }
      }
    }
    if(c == '{'){
      //Serial.println("in JSON");
      countDown = 7;;
    }
  }

  if(lastCommand != thisCommand){
    Serial.println("command changed");
    Serial.println(thisCommand);

    if(thisCommand == 1){
      modulate_out(on);
    }
    else{
      modulate_out(off);
    }

    lastCommand = thisCommand;
  }

  // if ten seconds have passed since your last connection,
  // then connect again and send data:
  if (millis() - lastConnectionTime > postingInterval) {
    httpRequest();
  }
}

// this method makes a HTTP connection to the server:
void httpRequest() {
  // close any connection before send a new request.
  // This will free the socket on the WiFi shield
  client.stop();

  // if there's a successful connection:
  if (client.connect(server, 80)) {
    //Serial.println("connecting...");
    // send the HTTP PUT request:
    client.println("GET /himitsu.json HTTP/1.1");
    client.println("Host: himitsu");
    client.println("Connection: close");
    client.println();

    // note the time that the connection was made:
    lastConnectionTime = millis();
  }
  else {
    // if you couldn't make a connection:
    Serial.println("connection failed");
  }
}


void printWiFiStatus() {
  // print the SSID of the network you're attached to:
  Serial.print("SSID: ");
  Serial.println(WiFi.SSID());

  // print your WiFi shield's IP address:
  IPAddress ip = WiFi.localIP();
  Serial.print("IP Address: ");
  Serial.println(ip);

  // print the received signal strength:
  long rssi = WiFi.RSSI();
  Serial.print("signal strength (RSSI):");
  Serial.print(rssi);
  Serial.println(" dBm");
}