WiFi Bulb

Essendo possessore di una Canon 100D e volendo fare dei filmati TimeLaps, ho avuto la necessità di creare un sistema di scatto multiplo e temporizzato e mi sono detto perchè non farlo con Arduino?

L'ESP8266 crea un access point Wifi al quale posso accedere con qualsiasi dispositivo.

Mediante l'interfaccia Web posso programmare il bulb con le opzioni :

  • Modalità messa a fuoco.
  • Tempo di messa a fuoco.
  • Tempo di bulb.
  • Tempo intervallo.
  • Numero di scatti.
  • Tipo HDR.
  • Tempo intervallo HDR.

Ho inserito un LED RGB che cambia colore in base allo stato del bulb

  • Arcobaleno - Bulb fermo.
  • Blu - Messa a fuoco.
  • Rosso - Scatto/Bulb.
  • Verde - Tempi di attesa / Intervalli.

E' possibile variare la luminosità del LED.

E' possibile richiedere lo stato del bulb con.

  • Il tempo trascorso da quando il bulb è acceso.
  • Il tempo di inizio processo.
  • Il tempo che è trascorso da inizio proceso.
  • Il tempo previsto per la finedel processo.
  • Lo stato corrente : fuoco / scatto / intervallo.
  • Il numero di scatti effettuato.

Materiale usato :

  • 1 - ESP8266
  • 2 - Optoisolatore EL817
  • 1 - LED WS2812
  • 2 - Resistenze 100 ohm
  • 2 - Resistenza 1K ohm
  • 1 - Regolatore di temsione LM317
  • 1 - Condensatore da 100 uF
  • 1 - Trimmer da 2K ohm
  • 1 - Connettore USB-A
  • 1 - Jack da 2,5 stereo
  • Vari strip maschi e femmina
  • Vari cavetti

Schema progetto :

Progetto Fritzing - ESP01 Shield

Progetto Fritzing - Alimentazione

Codice :


String WcbJs() {
  return F(
    "<script>"
    "function gebi(e) {"
    "return document.getElementById(e);"
    "}"
    "function relStato() {"
    "gebi('if_stato').contentWindow.location.reload(true);"
    "}"
    "function ocv(o, v, p, s) {"
    "gebi(o).value = v;"
    "var i = gebi('div_' + o);"
    "if (i != null) {"
    "i.innerText = '(' + v + ')';"
    "}"
    "if (p == true) {"
    "gebi('frmPost').submit();"
    "}"
    "if (s == true) {"
    "relStato();"
    "}"
    "}"
    "function ocgt(h) {"
    "window.location.href = h;"
    "}"
    "</script>"
  );
}

String WcbCss() {
  return F(
    "<style>"
    ".btn {"
    "width: 120px;"
    "}"
    "</style>"
  );
}

String WcbIco() {
  return F(
    "<link rel = \"shortcut icon\" href = \"data:image/x-icon;base64,AAABAAEAEBAAAAAAAABoBQAAFgAAACgAAAAQAAAAIAAAAAEACAAAAAAAAAEAAAAAAAAAAAAAAAEAAAAAAAAeHSEA/f3+AP79/gAlJCYAdHF0ACEfJAAfGB8AWXxnAOHu6AAfHSIAIB0iAEx9XQB3f38AV3plAP79/wDj8egA+vn6APz5+gBPfGAAHxsgAP37/QAhGyAAHx4gAFl7YwAfHSMATH1eAE19XgBSflsATIBeAHCQegDIxckAHRweAEx5WQD8/PsAU3xhAB8eIQD9/v4AU35kAP7+/gBMflwAaGdqAE9+XABMfV8ATX1fAFB9XwDj9OoArL2wAO3t7QCdn6IAHx4iAEt+XQBMfl0ATX5dAOLd4QBLfWAATn1gAGSFcgAdHCAA9/X4ACAcIAAkIyUAVXxjAJebngBLfl4ATH5eAPz3+wBNfl4ATn5eAPX68wBNfWEA/v74AGJlagD+/fsATUxOAFNWWwBQgGEAS3xcAC8uMABLe18A/f/+AE5+XwAeGh8A4+vlAC0sLgAeHR8AhIeGAB4cIgBJf10ASn9dAEl+YAD///8AHBsdALTKuACLnZMAIR0gABwZGwAjHSAAPj1BAFFMUACNlJQA3ezkACAfIwC4vL8AHBseAPr/+ACEmowA+/v7AP77+wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAJjkxMTExMTExMTExMTEjalMxMTExOWYBAR5bMTExMU0DMTEKQRcZQkILBxExMTExAzEJIUNCQkJCQkIzEFExZQMxNUJCQkJCQkJCQlcvGGUDMWlANDRCQkJCQhoSXQVlAxU2G0RIOEJCLWsuQhwTZQNHQg0kWlpYRVpaJkIzY2UDSkIiT1paMlBqWgJCJwxlAzs3LFxGJUJCHWg9QitnZQMxZEJCQkJCQkJCQioIVmUDMWIgKUJCQkJCQkBOKDFlAzFeFEs0P0JCQhpMOgAxZQMxMWAEUllCQkIPVTExMWVJMTExMTFfPjAGFjExMTFhWjwWFhYWFhYWFhYWFlQfDgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=\" / >"
  );
}

String WcbMeta() {
  return F(
    "<meta name=\"viewport\" content=\"width=device-width, user-scalable=no, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0\">"
    //"<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\" />"
    //"<meta charset=\"utf-8\" />"
  );
}

void handleGetstato() {
  server.sendHeader(F("Cache-Control"), F("no-cache, no-store, must-revalidate"));
  server.sendHeader(F("Pragma"), F("no-cache"));
  server.sendHeader(F("Expires"), F("-1"));

  String cnt;

  cnt += F(
    "<!DOCTYPE html>"
    "<html>"
    "<head>"
    "<link rel=\"shortcut icon\" href=\"data:image/x-icon; , \" type=\"image/x-icon\">"
    "<title></title>"
    "</head>"
    "<body>"
    "UP TIME : "
  );

  cnt += msToTime(millis());

  cnt += F(
    "<br />"
    "START TIME : "
  );

  cnt += msToTime(startTime);

  cnt += F(
    "<br />"
    "LEN TIME : "
  );

  unsigned long endTime = 0;

  if (var_maf == 1) {
    endTime += (var_int_maf * 10);
  }
  else {
    endTime += (var_int_maf * 10) * (var_sct - scatti);
  }

  endTime += (var_tis * 10) * (var_sct - scatti);
  endTime += (var_blb * 10) * (var_sct - scatti);

  if (var_hdr > 0) {
    endTime += ((var_int_hdr * 10) * 2) * (var_sct - scatti);
    switch (var_hdr)
    {
    case 1:
      endTime += (((var_blb * 10) / 2) * 2) * (var_sct - scatti);
      break;
    case 2:
      endTime += (((var_blb * 10) / 4) * 2) * (var_sct - scatti);
      break;
    }
  }

  endTime += (var_int * 10) * (var_sct - scatti - 1);

  cnt += msToTime(endTime);

  cnt += F(
    "<br />"
    "END TIME : "
  );

  cnt += msToTime(endTime + startTime);

  cnt += F(
    "<br />"
    "STATO : "
  );

  if (startblb) {
    cnt += F("IN FUNZIONE");
  }
  else {
    cnt += F("FERMO");
  }

  cnt += F(
    "<br />"
    "SCATTO : "
  );
  cnt += String(scatti);
  cnt += F("/");
  cnt += String(var_sct);
  cnt += F(
    "<br />"
    "STEP : "
  );

  switch (stepBlb)
  {
  case 1: // messa a fuovo
    cnt += F("MESSA A FUOCO");

    break;
  case 2: // tempo inizio scatto
    cnt += F("TEMPO INIZIO SCATTO");

    break;
  case 3: // scatto / hdr step 1
    cnt += F("SCATTO");

    break;
  case 4: // intervallo hdr
    cnt += F("INTERVALLO HDR");

    break;
  case 5: // hdr step 2
    cnt += F("SCATTO HDR");

    break;
  case 6: // intervallo hdr
    cnt += F("INTERVALLO HDR");

    break;
  case 7: // hdr step 3
    cnt += F("SCATTO HDR");

    break;
  case 8: // controllo
    cnt += F("CONTROLLO");

    break;
  case 9: // intervallo
    cnt += F("INTERVALLO");

    break;
  default:
    cnt += F("...");

    break;
  }

  cnt += F(
    "</body>"
    "</html>"
  );

  server.setContentLength(cnt.length());
  server.send(200, F("text/html"), cnt);
  server.client().stop();

}

void handleReturnPost() {
  server.sendHeader(F("Cache-Control"), F("no-cache, no-store, must-revalidate"));
  server.sendHeader(F("Pragma"), F("no-cache"));
  server.sendHeader(F("Expires"), F("-1"));
  String cnt = F("");
  server.setContentLength(cnt.length());
  server.send(302, F("text/plain"), cnt);
  server.client().stop();
}

void handlePostset() {
  var_maf = server.arg(F("maf")).toInt();
  var_int_maf = server.arg(F("int_maf")).toInt();
  var_tis = server.arg(F("tis")).toInt();
  var_blb = server.arg(F("blb")).toInt();
  var_int = server.arg(F("int")).toInt();
  var_sct = server.arg(F("sct")).toInt();
  var_hdr = server.arg(F("hdr")).toInt();
  var_int_hdr = server.arg(F("int_hdr")).toInt();
  var_cmd = server.arg(F("cmd")).toInt();

  handleReturnPost();

  switch (var_cmd)
  {
  case 1: // start/stop
    startblb = !startblb;
    if (startblb) {
      startTime = millis();
      if (scatti >= var_sct) {
        scatti = 0;
        stepBlb = 0;
      }
    }
    else {
      scatto_su();
      if (var_maf == 2) {
        fuoco_su();
      }
    }
    tmrBlb = 0;
    break;
  case 2: // reset
    scatti = 0;
    startTime = 0;
    scatto_su();
    fuoco_su();
    tmrBlb = 0;
    stepBlb = 0;
    break;
  case 5: // led +
    if (led_bright > 10) {
      led_bright += 10;
    }
    else {
      led_bright += 1;
    }
    break;
  case 6: // led -
    if (led_bright > 10) {
      led_bright -= 10;
    }
    else {
      led_bright -= 1;
    }
    break;
  case 7: // led 0%
    led_bright = 0;
    break;
  case 8: // led 50%
    led_bright = 120;
    break;
  case 9: // led 100%
    led_bright = 250;
    break;
  }

  var_cmd = 0;

}

void handleRoot() {
  server.sendHeader(F("Cache-Control"), F("no-cache, no-store, must-revalidate"));
  server.sendHeader(F("Pragma"), F("no-cache"));
  server.sendHeader(F("Expires"), F("-1"));
  server.setContentLength(CONTENT_LENGTH_UNKNOWN);
  server.send(200, F("text/html"), F(""));
  server.sendContent(F(
    "<!DOCTYPE html>"
    "<html>"
    "<head>"
  ));
  server.sendContent(WcbMeta());
  server.sendContent(WcbIco());
  server.sendContent(WcbCss());
  server.sendContent(WcbJs());
  server.sendContent(F(
    "<title>WIFI BULB</title>"
    "</head>"
    "<body>"
    "<h1>WIFI BULB</h1>"
    "<fieldset>"
    "<legend>MENU</legend>"
    "<input type=\"button\" class=\"btn\" value=\"SETUP\" onclick=\"ocgt('/setup')\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>MESSA A FUOCO</legend>"
    "<a id=\"div_maf\">("
  ));
  server.sendContent(String(var_maf));
  server.sendContent(F(
    ")</a>"
    "<br />"
    "<input type=\"button\" class=\"btn\" value=\"1) PRIMA FOTO\" onclick=\"ocv('maf', 1)\" />"
    "<input type=\"button\" class=\"btn\" value=\"2) OGNI FOTO\" onclick=\"ocv('maf', 2)\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>TEMPO INTERVALLO MESSA A FUOCO</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_int_maf));
  server.sendContent(F(
    "\" min=\"1\" max=\"65535\" onchange=\"ocv('int_maf', this.value)\" />/100 sec"
    "</fieldset>"
    "<fieldset>"
    "<legend>TEMPO INIZIO SCATTO</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_tis));
  server.sendContent(F(
    "\" min=\"0\" max=\"65535\" onchange=\"ocv('tis', this.value)\" />/100 sec"
    "</fieldset>"
    "<fieldset>"
    "<legend>TEMPO BULB</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_blb));
  server.sendContent(F(
    "\" min=\"1\" max=\"65535\" onchange=\"ocv('blb', this.value)\" />/100 sec"
    "</fieldset>"
    "<fieldset>"
    "<legend>TEMPO INTERVALLO</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_int));
  server.sendContent(F(
    "\" min=\"1\" max=\"65535\" onchange=\"ocv('int', this.value)\" />/100 sec"
    "</fieldset>"
    "<fieldset>"
    "<legend>NUMERO SCATTI</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_sct));
  server.sendContent(F(
    "\" min=\"1\" max=\"65535\" onchange=\"ocv('sct', this.value)\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>TIPO HDR</legend>"
    "<a id=\"div_hdr\">("
  ));
  server.sendContent(String(var_hdr));
  server.sendContent(F(
    ")</a>"
    "<br />"
    "<input type=\"button\" class=\"btn\" value=\"0) NO\" onclick=\"ocv('hdr', 0)\" />"
    "<input type=\"button\" class=\"btn\" value=\"1) 1 EV\" onclick=\"ocv('hdr', 1)\" />"
    "<input type=\"button\" class=\"btn\" value=\"2) 2 EV\" onclick=\"ocv('hdr', 2)\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>TEMPO INTERVALLO HDR</legend>"
    "<input type=\"number\" value=\""
  ));
  server.sendContent(String(var_int_hdr));
  server.sendContent(F(
    "\" min=\"1\" max=\"65535\" onchange=\"ocv('int_hdr', this.value)\" />/100 sec"
    "</fieldset>"
    "<fieldset>"
    "<legend>COMANDI</legend>"
    "<input type=\"button\" class=\"btn\" value=\"START\\PAUSA\" onclick=\"ocv('cmd', 1, true, true)\" />"
    "<input type=\"button\" class=\"btn\" value=\"RESETTA\" onclick=\"ocv('cmd', 2, true, true)\" />"
    "<input type=\"button\" class=\"btn\" value=\"IMPOSTA\" onclick=\"ocv('cmd', 0, true, true);\" />"
    "<input type=\"button\" class=\"btn\" value=\"AGGIORNA STATO\" onclick=\"relStato();\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>LED LUMINOSITA'</legend>"
    "<input type=\"button\" class=\"btn\" value=\"+\" onclick=\"ocv('cmd', 5, true, false)\" />"
    "<input type=\"button\" class=\"btn\" value=\"-\" onclick=\"ocv('cmd', 6, true, false)\" />"
    "<input type=\"button\" class=\"btn\" value=\"0%\" onclick=\"ocv('cmd', 7, true, false)\" />"
    "<input type=\"button\" class=\"btn\" value=\"50%\" onclick=\"ocv('cmd', 8, true, false)\" />"
    "<input type=\"button\" class=\"btn\" value=\"100%\" onclick=\"ocv('cmd', 9, true, false)\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>STATO</legend>"
    "<iframe id=\"if_stato\" name=\"if_stato\" style=\"width: 100% ;border: none;\"></iframe>"
    "</fieldset>"
    "<form id='frmPost' name='frmPost' method='POST' action='postset' target='if_post' style=\"display: none;\">"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_maf));
  server.sendContent(F(
    "' id='maf' name='maf'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_int_maf));
  server.sendContent(F(
    "' id='int_maf' name='int_maf'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_tis));
  server.sendContent(F(
    "' id='tis' name='tis'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_blb));
  server.sendContent(F(
    "' id='blb' name='blb'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_int));
  server.sendContent(F(
    "' id='int' name='int'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_sct));
  server.sendContent(F(
    "' id='sct' name='sct'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_hdr));
  server.sendContent(F(
    "' id='hdr' name='hdr'>"
    "<input type='hidden' value='"
  ));
  server.sendContent(String(var_int_hdr));
  server.sendContent(F(
    "' id='int_hdr' name='int_hdr'>"
    "<input type='hidden' value='0' id='cmd' name='cmd'>"
    "</form>"
    "<iframe src=\"\" id=\"if_post\" name=\"if_post\" style=\"display: none;\"></iframe>"
    "<script>"
    "if (window.addEventListener) {"
    "window.addEventListener('load', function(){document.getElementById('if_stato').contentWindow.location.href = '/getstato';}, false);"
    "} else if (window.attachEvent) {"
    "window.attachEvent('onload', function(){document.getElementById('if_stato').contentWindow.location.href = '/getstato';});}"
    "</script>"
    "</body>"
    "</html>"
  ));
  server.client().stop();
}

void handleSetup() {
  server.sendHeader(F("Cache-Control"), F("no-cache, no-store, must-revalidate"));
  server.sendHeader(F("Pragma"), F("no-cache"));
  server.sendHeader(F("Expires"), F("-1"));
  server.setContentLength(CONTENT_LENGTH_UNKNOWN);
  server.send(200, F("text/html"), F(""));
  server.sendContent(F(
    "<html><head>"
  ));
  server.sendContent(WcbMeta());
  server.sendContent(WcbIco());
  server.sendContent(WcbCss());
  server.sendContent(WcbJs());
  server.sendContent(F(
    "<title>WIFI BULB</title>"
    "</head><body>"
    "<h1>SETUP</h1>"
    "<fieldset>"
    "<legend>MENU</legend>"
    "<input type=\"button\" value=\"HOME\" class=\"btn\" onclick=\"ocgt('/')\" />"
    "</fieldset>"
    "<fieldset>"
    "<legend>AP CONFIG</legend>"
    "<table>"
  ));
  server.sendContent(String(F("<tr><td>SSID</td><td>")) + String(softAP_ssid) + String(F("</td></tr>")));
  server.sendContent(String(F("<tr><td>IP</td><td>")) + toStringIp(WiFi.softAPIP()) + String(F("</td></tr>")));
  server.sendContent(String(F("<tr><td>CH</td><td>")) + String(WiFi.channel()) + String(F("</td></tr>")));
  server.sendContent(String(F("<tr><td>PSW</td><td>")) + String(softAP_password) + String(F("</td></tr>")));
  
  server.sendContent(F(
    "</table>"
    "</fieldset>"
    "</body>"
    "</html>"
  ));
  server.client().stop();
}

boolean isIp(String str) {
  for (int i = 0; i < str.length(); i++) {
    int c = str.charAt(i);
    if (c != '.' && (c < '0' || c > '9')) {
      return false;
    }
  }
  return true;
}

String toStringIp(IPAddress ip) {
  String res = "";
  for (int i = 0; i < 3; i++) {
    res += String((ip >> (8 * i)) & 0xFF) + ".";
  }
  res += String(((ip >> 8 * 3)) & 0xFF);
  return res;
}

String msToTime(unsigned long mll) {
  int d = int(mll / 86400000);
  unsigned long over = mll % 86400000;
  int h = int(over / 3600000);
  over = over % 3600000;
  int m = int(over / 60000);
  over = int(over % 60000);
  int s = int(over / 1000);
  int ms = int(over % 1000);

  return String(d) + F("d ") + String(h) + F("h ") + String(m) + F("m ") + String(s) + F("s ") + String(ms) + F("ms");
}

#include <Adafruit_NeoPixel.h>

// LED
#define PIN_LED 2
#define NUM_LEDS 1
#define LEDS_HIGH 255

byte led_bright = 10;
byte led_fade = 0;
Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LEDS, PIN_LED, NEO_GRB + NEO_KHZ800);

// bulb
#define PIN_SCATTO 3
#define PIN_FUOCO 1

byte var_maf = 2;
unsigned int var_int_maf = 100;
unsigned int var_tis = 0;
unsigned int var_blb = 100;
unsigned int var_int = 100;
unsigned int var_sct = 1;
byte var_hdr = 0;
unsigned int var_int_hdr = 50;
byte var_cmd = 0;
unsigned int scatti = 0;
unsigned long tmrBlb = 0;
unsigned long startTime = 0;
byte stepBlb = 0;
bool startblb = false;

void nextStep() {
  stepBlb++;
  tmrBlb = 0;
}

void setLedColor(unsigned int r, unsigned int g, unsigned int b) {
  strip.setPixelColor(0, strip.Color(r, g, b));
  strip.setBrightness(led_bright);
  strip.show();
}

void fuoco_giu() {
  digitalWrite(PIN_FUOCO, LOW);
  setLedColor(0, 0, LEDS_HIGH);
}

void fuoco_su() {
  digitalWrite(PIN_FUOCO, HIGH);
  setLedColor(0, 0, 0);
}

void scatto_giu() {
  digitalWrite(PIN_SCATTO, LOW);
  setLedColor(LEDS_HIGH, 0, 0);
}

void scatto_su() {
  digitalWrite(PIN_SCATTO, HIGH);
  setLedColor(0, 0, 0);
}

void intervallo_hdr() {
  if (var_hdr == 0) {
    nextStep();
  }
  else {
    if (tmrBlb == 0) {
      tmrBlb = millis() + (var_int_hdr * 10);
      setLedColor(0, LEDS_HIGH, 0);
    }
    if (millis() > tmrBlb) {
      setLedColor(0, 0, 0);
      nextStep();
    }
  }

}

void showLedBusy() {
  led_fade++;

  byte r = 0;
  byte g = 0;
  byte b = 0;

  byte WheelPos = 255 - (led_fade & 255);

  if (WheelPos < 85) {
    r = (255 - WheelPos * 3);
    g = 0;
    b = (WheelPos * 3);

  }
  else if (WheelPos < 170) {
    WheelPos -= 85;
    r = 0;
    g = (WheelPos * 3);
    b = (255 - WheelPos * 3);

  }
  else {
    WheelPos -= 170;
    r = (WheelPos * 3);
    g = (255 - WheelPos * 3);
    b = 0;

  }
  setLedColor(r, g, b);
}

void WCB_setup() {

  pinMode(PIN_SCATTO, OUTPUT);
  digitalWrite(PIN_SCATTO, HIGH);
  pinMode(PIN_FUOCO, OUTPUT);
  digitalWrite(PIN_FUOCO, HIGH);

  strip.begin();
  strip.setBrightness(led_bright);
  setLedColor(LEDS_HIGH, LEDS_HIGH, LEDS_HIGH);
}

void WCB_loop() {
  // BULB
  if (startblb) {
    switch (stepBlb)
    {
    case 1: // messa a fuovo
      if ((var_maf == 1 && scatti == 0) || (var_maf == 2)) {
        if (tmrBlb == 0) {
          tmrBlb = millis() + (var_int_maf * 10);
          fuoco_giu();
        }
        if (millis() > tmrBlb) {
          nextStep();
        }
      }
      else {
        nextStep();
      }

      break;
    case 2: // tempo inizio scatto
      if (tmrBlb == 0) {
        tmrBlb = millis() + (var_tis * 10);
        setLedColor(0, LEDS_HIGH, 0);
      }
      if (millis() > tmrBlb) {
        nextStep();
        setLedColor(0, 0, 0);
      }

      break;
    case 3: // scatto / hdr step 1
      if (tmrBlb == 0) {
        tmrBlb = millis() + (var_blb * 10);
        scatto_giu();
      }
      if (millis() > tmrBlb) {
        scatto_su();
        nextStep();
      }

      break;
    case 4: // intervallo hdr
      intervallo_hdr();

      break;
    case 5: // hdr step 2
      if (var_hdr == 0) {
        nextStep();
      }
      else {
        if (tmrBlb == 0) {
          switch (var_hdr)
          {
          case 1:
            tmrBlb = millis() + ((var_blb * 10) / 2);
            break;
          case 2:
            tmrBlb = millis() + ((var_blb * 10) / 4);
            break;
          }
          scatto_giu();
        }
        if (millis() > tmrBlb) {
          scatto_su();
          nextStep();
        }
      }

      break;
    case 6: // intervallo hdr
      intervallo_hdr();

      break;
    case 7: // hdr step 3
      if (var_hdr == 0) {
        nextStep();
      }
      else {
        if (tmrBlb == 0) {
          switch (var_hdr)
          {
          case 1:
            tmrBlb = millis() + ((var_blb * 10) * 2);
            break;
          case 2:
            tmrBlb = millis() + ((var_blb * 10) * 4);
            break;
          }
          scatto_giu();
        }
        if (millis() > tmrBlb) {
          scatto_su();
          nextStep();
        }
      }

      break;
    case 8: // controllo
      scatti++;
      if (scatti >= var_sct) {
        startblb = false;
        scatto_su();
        fuoco_su();
        stepBlb = 0;
      }
      else {
        if (var_maf == 2) {
          fuoco_su();
        }
        nextStep();
      }

      break;
    case 9: // intervallo
      if (tmrBlb == 0) {
        tmrBlb = millis() + (var_int * 10);
        setLedColor(0, LEDS_HIGH, 0);
      }
      if (millis() > tmrBlb) {
        setLedColor(0, 0, 0);
        nextStep();
      }

      break;
    default:
      stepBlb = 1;
      break;
    }
  }
  else {
    if (tmrBlb == 0) {
      tmrBlb = millis() + 10;
    }
    if (millis() > tmrBlb) {
      showLedBusy();
      tmrBlb = 0;
    }
  }
}

#include <ESP8266WiFi.h>
#include <WiFiClient.h>
#include <ESP8266WebServer.h>
#include <DNSServer.h>

// DNS server
#define DNS_PORT 53

DNSServer dnsServer;

// Web server
ESP8266WebServer server(80);

// Soft AP
#define softAP_ssid "WCB_AP"
#define softAP_password "12345678" 
#define canale 11


IPAddress apIP(192, 168, 4, 1);

void setup() {

  WCB_setup();

  WiFi.mode(WIFI_AP); 
  WiFi.softAPConfig(apIP, apIP, IPAddress(255, 255, 255, 0));
  WiFi.softAP(softAP_ssid, softAP_password, canale);
  delay(500);

  dnsServer.setErrorReplyCode(DNSReplyCode::NoError);
  dnsServer.start(DNS_PORT, F("*"), apIP);

  server.on("/", handleRoot);
  server.on("/setup", handleSetup);
  server.on("/postset", handlePostset);
  server.on("/getstato", handleGetstato);
  server.onNotFound(handleRoot);
  server.begin(); 

}

void loop() {

  WCB_loop();
  dnsServer.processNextRequest();
  server.handleClient();

}


 

Galleria :

Browser.jpg Jeck.jpg Screenshot1.png

Screenshot2.png Screenshot3.png WifiBulb-ALIM_bb.jpg

WifiBulb-ALIM_schem.jpg WifiBulb-ESP01_bb.jpg WifiBulb-ESP01_schem.jpg