[SOLVED] Sparkfun Blynk Board - re-connect to app (restore original firmware)

Hello,
I purchased a blynk board about a year ago and it comes preloaded with code on it so that it is broadcasting a wifi signal for setup. Once I connected the blynk board to my app on my phone, I uploaded new code to the blynk board so that I could receive email notifications.

The app has now lost communication with the blynk board, if I go through the “setup new device” on the app, the blynk board does not show up on the list of available wifi signals.

I’m assuming I need to upload the old sparkfun code to the blynk board but I can’t find it anywhere online.

Any ideas how to re-connect?

Thanks!

I think this might help…

From this page:

https://learn.sparkfun.com/tutorials/getting-started-with-the-sparkfun-blynk-board#resources

you can go to Blynk Board Arduino Firmware:

Thanks @Gunner !

Hello again, still having trouble…
I have installed the FTDI drivers, manually pasted the blynk libraries into my arduino libraries folder, installed the blynk libraries in "manage libraries, and finally added the blynk board to my “boards”.
When I upload the firmware shown below, I get the following error: ‘WidgetLCD’ does not name a type.

Any ideas?

/******************************************************************************
BlynkBoard_BlynkMode.ino
BlynkBoard Firmware: Blynk Demo Source
Jim Lindblom @ SparkFun Electronics
February 24, 2016
https://github.com/sparkfun/Blynk_Board_ESP8266/Firmware
This file, part of the BlynkBoard Firmware, implements all "Blynk Mode"
functions of the BlynkBoard Core Firmware. That includes managing the Blynk
connection and ~10 example experiments, which can be conducted without
reprogramming the Blynk Board.
 Supported Experiment list:
 0: RGB LED - ZeRGBa (V0)
 2: 5 LED - Button (D5)
 3: 0 Button - Virtual LED (V3)
      2~: 0 Button - tweet, would need to modify button interrupt handler
 4: Humidity and temperature to <strike>gauge</strike> value displays
 5: RGB control from <strike>Zebra widet</strike> Sliders
 6. Incoming serial on hardware port sends to terminal in Blynk
 7. ADC hooked to VIN pin on graph
 8. TODO: Alligator clips connected to GPIO 12(?) send an email
 9. TODO: Timer triggers relay
 10. TODO: IMU graphs to phone 
Resources:
Blynk Arduino Library: https://github.com/blynkkk/blynk-library/releases/tag/v0.3.1
SparkFun HTU21D Library: https://github.com/sparkfun/SparkFun_HTU21D_Breakout_Arduino_Library/releases/tag/V_1.1.1
License:
This is released under the MIT license (http://opensource.org/licenses/MIT).
Please see the included LICENSE.md for more information.
Development environment specifics:
Arduino IDE 1.6.7
SparkFun BlynkBoard - ESP8266
******************************************************************************/

#include <Wire.h>
#include "SparkFunHTU21D.h"
#include <SparkFunTSL2561.h>
#include "Servo.h"
HTU21D thSense;

bool scanI2C(uint8_t address);

////////////////////////////////////
// Blynk Virtual Variable Mapping //
//////////////////////////////////// // Experiment #(s)
#define RGB_VIRTUAL               V0 // 0, 6
#define BUTTON_VIRTUAL            V1 // 1
#define RED_VIRTUAL               V2 // 3
#define GREEN_VIRTUAL             V3 // 3
#define BLUE_VIRTUAL              V4 // 3
#define TEMPERATURE_F_VIRTUAL     V5 // 4
#define TEMPERATURE_C_VIRTUAL     V6 // 4
#define HUMIDITY_VIRTUAL          V7 // 4
#define ADC_VOLTAGE_VIRTUAL       V8 // 5
#define RGB_RAINBOW_VIRTUAL       V9 // 6
#define LCD_VIRTUAL               V10 // 8
#define LCD_TEMPHUMID_VIRTUAL     V11 // 8
#define LCD_STATS_VIRTUAL         V12 // 8
#define LCD_RUNTIME_VIRTUAL       V13 // 8
#define SERVO_XY_VIRTUAL          V14
#define RGB_MAX_BRIGHTNESS_VIRTUAL V15// 0, 6
#define SERVO_MAX_VIRTUAL         V16 // 9
#define SERVO_ANGLE_VIRUTAL       V17 // 9
#define LUX_VIRTUAL               V18 // 10
//! V19 available
#define ADC_BATT_VIRTUAL          V20 // 11
#define SERIAL_VIRTUAL            V21 // 12, 15
//! V22 available
#define TWITTER_THRESHOLD_VIRTUAL V23 // 13
#define TWITTER_RATE_VIRTUAL      V24 // 13
#define DOOR_STATE_VIRTUAL        V25 // 14
//! V26 available
#define EMAIL_ENABLED_VIRTUAL     V27 // 15
#define TEMP_OFFSET_VIRTUAL       V28 // 4
#define RGB_STRIP_NUM_VIRTUAL     V29 // 6
#define RUNTIME_VIRTUAL           V30 // Utility
#define RESET_VIRTUAL             V31 // Utility

WidgetLCD thLCD(LCD_VIRTUAL); // LCD widget, updated in blynkLoop
#define LCD_SPLASH_UPDATE_RATE 10000
unsigned long lastLCDSplashUpdate = 0;

// BLYNK_CONNECTED is called the first time the Blynk Board
// connects to Blynk. Then any time it reconnects later on.
bool firstConnect = true;
BLYNK_CONNECTED() 
{
  BB_DEBUG("Connected.");
  if (firstConnect)
  {
    BB_DEBUG("First connect.");
    // Print a message to the LCD the first time connecting.
    thLCD.print(0, 0, "sfe.io/blynk    ");
    thLCD.print(0, 1, "       for more!");
    
    firstConnect = false;
  }
  Blynk.syncAll(); // Sync all virtual variables
}

/* 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
 0 Experiment 0: zeRGBa                0
 0 Widget(s):                          0
 0  - zeRGBa: Merge, V0                0
 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 */
byte blynkRed = 0; // Keeps track of red value
byte blynkGreen = 0; // Keeps track of green value
byte blynkBlue = 0; // Keeps track of blue value
unsigned int rgbMaxBrightness = DEFAULT_MAX_BRIGHTNESS;

void updateBlynkRGB(void)
{
  if (!rgbSetByProject) // If the setByProject flag isn't set
  { // The LED should still be pulsing
    blinker.detach(); // Detach the rgbBlink timer
    rgbSetByProject = true; // Set the flag
  }
  // Show the new LED color:  
  for (int i=0; i<rgb.numPixels(); i++)
    rgb.setPixelColor(i, rgb.Color(map(blynkRed, 0, 255, 0, rgbMaxBrightness), 
                                   map(blynkGreen, 0, 255, 0, rgbMaxBrightness),
                                   map(blynkBlue, 0, 255, 0, rgbMaxBrightness)));
  rgb.show();
}

bool firstRGBWrite = true; // On startup
BLYNK_WRITE(RGB_VIRTUAL)
{
  // RGB widget may send invalid buffer data. If we try to read those in
  // the ESP8266 crashes. At a minimum, for valid data, the buffer 
  // length should be >=5. ("0,0,0" ?)
  if (param.getLength() < 5)
    return;
  
  blynkRed = param[0].asInt();
  blynkGreen = param[1].asInt();
  blynkBlue = param[2].asInt();

  BB_DEBUG("Blynk Write RGB: " + String(blynkRed) + ", " + 
          String(blynkGreen) + ", " + String(blynkBlue) + 
          " (Max: " + String(rgbMaxBrightness) + ")");
  // Don't update the RGB if this is the first time. syncAll
  // will call this function initially. We want to breathe
  // the status LED instead.
  if (!firstRGBWrite)
  {
    if (!rgbSetByProject) // If blinker timer is attached
    {
      blinker.detach(); // Detach it
      rgbSetByProject = true;
    }
    // Set all attached pixels (usually it'll only be 1)
    updateBlynkRGB();
  }
  else
  {
    firstRGBWrite = false;
  }
}

/* 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
 1 Experiment 1: Button                1
 1 Widget(s):                          1
 1  - Button: GP5, Push or switch      1
 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 */
// No variables required - Use GP5 directly

/* 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2
 2 Experiment 2: LED                   2
 2 Widget(s):                          2
 2  - LED: V1                          2
 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 */
// To update the buttonLED widget, buttonUpdate() is called through
// a pin-change interrupt.
WidgetLED buttonLED(BUTTON_VIRTUAL); // LED widget in Blynk App
unsigned long lastButtonUpdate = 0; // millis()-tracking button update rate
#define BUTTON_UPDATE_RATE 100 // Button update rate in ms
int lastButtonState = -1; // Keeps track of last button state push

void buttonUpdate(void) 
{
  int buttonState = digitalRead(BUTTON_PIN); // Read button state
  if (buttonState != lastButtonState) // If the state has changed
  {
    lastButtonState = buttonState; // Update last state
    if (buttonState) // If the button is released (HIGH)
      buttonLED.off(); // Turn the LED off
    else // If the button is pressed (LOW)
      buttonLED.on(); // Turn the LED on
  }
}

/* 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
 3 Experiment 3: Sliders               3
 3 Widget(s):                          3
 3  - Large Slider: GP5, D5, 0-255     3
 3  - Slider: Red, V2, 0-255           3
 3  - Slider: Green, V3, 0-255         3
 3  - Slider: Blue, V4, 0-255          3
 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 */
// GP5 variables not necessary - directly controlled

BLYNK_WRITE(RED_VIRTUAL)
{
  int redIn = param.asInt(); // Read the value in
  BB_DEBUG("Blynk Write red: " + String(redIn));
  redIn = constrain(redIn, 0, 255); // Keep it between 0-255
  blynkRed = redIn; // Update the global variable
  updateBlynkRGB(); // Show the color on the LED
}

BLYNK_WRITE(GREEN_VIRTUAL)
{
  int greenIn = param.asInt(); // Read the value in
  BB_DEBUG("Blynk Write green: " + String(greenIn));
  greenIn = constrain(greenIn, 0, 255); // Keep it between 0-255
  blynkGreen = greenIn; // Update the global variable
  updateBlynkRGB(); // Show the color on the LED
}

BLYNK_WRITE(BLUE_VIRTUAL)
{
  int blueIn = param.asInt(); // Read the value in
  BB_DEBUG("Blynk Write blue: " + String(blueIn));
  blueIn = constrain(blueIn, 0, 255); // Keep it between 0-255
  blynkBlue = blueIn; // Update the global variable
  updateBlynkRGB(); // Show the color on the LED
}

BLYNK_WRITE(RGB_MAX_BRIGHTNESS_VIRTUAL)
{
  int brightnessIn = param.asInt();
  brightnessIn = constrain(brightnessIn, 1, 255);
  BB_DEBUG("Setting RGB max brightness to: " + String(rgbMaxBrightness));
  rgbMaxBrightness = brightnessIn;
  updateBlynkRGB(); // Show the color on the LED
}

/* 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4
 4 Experiment 4: Values                4
 4 Widget(s):                          4
 4  - Value: TempF, V5, 0-1023, 1 s    4
 4  - Value: TempC, V6, 0-1023, 1 s    4
 4  - Value: Humidity, V7, 0-1023, 1 s 4
 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 */
// Value ranges are ignored once values are written
// Board runs hot, subtract an offset to try to compensate:
float tempCOffset = 0; //-8.33;
BLYNK_READ(TEMPERATURE_F_VIRTUAL)
{
  float tempC = thSense.readTemperature(); // Read from the temperature sensor
  tempC += tempCOffset; // Add any offset
  float tempF = tempC * 9.0 / 5.0 + 32.0; // Convert to farenheit
  // Create a formatted string with 1 decimal point:
  Blynk.virtualWrite(TEMPERATURE_F_VIRTUAL, tempF); // Update Blynk virtual value
  BB_DEBUG("Blynk Read TempF: " + String(tempF));
}

BLYNK_READ(TEMPERATURE_C_VIRTUAL)
{
  float tempC = thSense.readTemperature(); // Read from the temperature sensor
  tempC += tempCOffset; // Add any offset
  Blynk.virtualWrite(TEMPERATURE_C_VIRTUAL, tempC); // Update Blynk virtual value
  BB_DEBUG("Blynk Read TempC: " + String(tempC));
}

BLYNK_READ(HUMIDITY_VIRTUAL)
{
  float humidity = thSense.readHumidity(); // Read from humidity sensor
  Blynk.virtualWrite(HUMIDITY_VIRTUAL, humidity); // Update Blynk virtual value
  BB_DEBUG("Blynk Read Humidity: " + String(humidity));
}

BLYNK_WRITE(TEMP_OFFSET_VIRTUAL) // Very optional virtual to set the tempC offset
{
  tempCOffset = param.asInt();
  BB_DEBUG("Blynk TempC Offset: " + String(tempCOffset));
}

/* 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5
 5 Experiment 5: Gauge           5
 5 Widget(s):                    5
 5  - Gauge: ADC0, 0-1023, 1 sec 5
 5  - Gauge: V8, 0-4, 1 sec      5
 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 */
// ADC is read directly to a gauge
// Voltage is read to V8
BLYNK_READ(ADC_VOLTAGE_VIRTUAL)
{
  float adcRaw = analogRead(A0); // Read in A0
  // Divide by 1024, then multiply by the hard-wired voltage divider max (3.2)
  float voltage = ((float)adcRaw / 1024.0) * ADC_VOLTAGE_DIVIDER;
  Blynk.virtualWrite(ADC_VOLTAGE_VIRTUAL, voltage); // Output value to Blynk
  BB_DEBUG("Blynk DC Voltage: " + String(voltage));
}

/* 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
 6 Experiment 6: zeRGBa                6
 6 Widget(s):                          6
 6  - zeRGBa: Merge, V0                6
 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 */
Ticker rgbRainbowTicker; // Timer to set RGB rainbow mode

void rgbRainbow(void)
{
  static byte rainbowCounter = 0; // cycles from 0-255
  // From Wheel function in Adafruit_Neopixel strand example:
  //uint32_t rainbowColor;
  uint8_t rainbowRed, rainbowGreen, rainbowBlue;
  for (int i=0; i<rgb.numPixels(); i++) // numPixels may just be 1
  {
    byte colorPos = i + rainbowCounter; 
    if (colorPos < 85)
    {
      rainbowRed = 255 - colorPos * 3;
      rainbowGreen = 0;
      rainbowBlue = colorPos * 3;
    }
    else if (colorPos < 170)
    {
      colorPos -= 85;
      rainbowRed = 0;
      rainbowGreen = colorPos * 3;
      rainbowBlue = 255 - colorPos *3;
    }
    else
    {
      colorPos -= 170;
      rainbowRed = colorPos * 3;
      rainbowGreen = 255 - colorPos *3;
      rainbowBlue = 0;
    }
    rainbowRed = map(rainbowRed, 0, 255, 0, rgbMaxBrightness);
    rainbowGreen = map(rainbowGreen, 0, 255, 0, rgbMaxBrightness);
    rainbowBlue = map(rainbowBlue, 0, 255, 0, rgbMaxBrightness);
    
    rgb.setPixelColor(i, rgb.Color(rainbowRed, rainbowGreen, rainbowBlue)); // Set the pixel color
  }
  rgb.show(); // Actually set the LED
  rainbowCounter++; // IncremenBUTTONt counter, may roll over to 0
}

BLYNK_WRITE(RGB_RAINBOW_VIRTUAL)
{
  int rainbowState = param.asInt();
  BB_DEBUG("Rainbow Write: " + String(rainbowState));
  if (rainbowState) // If parameter is 1
  {
    blinker.detach(); // Detactch the status LED 
    rgbRainbowTicker.attach_ms(20, rgbRainbow);
    rgbSetByProject = true;
  }
  else
  {
    rgbRainbowTicker.detach();
    for (int i=0; i<rgb.numPixels(); i++)
      rgb.setPixelColor(i, 0);
    rgb.show();
    blinker.attach_ms(1, blinkRGBTimer);
    rgbSetByProject = false;
  }
}

BLYNK_WRITE(RGB_STRIP_NUM_VIRTUAL)
{
  int ledCount = param.asInt();
  if (ledCount <= 0) ledCount = 1;
  BB_DEBUG("RGB Strip length: " + String(ledCount));
  rgb.updateLength(ledCount);
}

/* 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7
 7 Experiment 7: Timer                 7
 7 Widget(s):                          7
 7  - Timer: Relay, GP12, Start, Stop  7
 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 7 */
// No functions or variables required

/* 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8
 8 Experiment 8: LCD                   8
 8 Widget(s):                          8
 8  - LCD: Advanced, V10               8
 8  - Button: TempHumid, V11           8
 8  - Button: Stats, V12               8
 8  - Button: Runtime, V13             8
 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 8 */
bool lcdSetByProject = false;
BLYNK_WRITE(LCD_TEMPHUMID_VIRTUAL)
{
  if (param.asInt() > 0)
  {
    if (!lcdSetByProject) lcdSetByProject = true;
    float humd = thSense.readHumidity(); // Read humidity
    float tempC = thSense.readTemperature(); // Read temperature
    float tempF = tempC * 9.0 / 5.0 + 32.0; // Calculate farenheit
    String tempLine = String(tempF, 2) + "F / "+ String(tempC, 2) + "C";
    String humidityLine = "Humidity: " + String(humd, 1) + "%";
    thLCD.clear(); // Clear the LCD
    thLCD.print(0, 0, tempLine.c_str());
    thLCD.print(0, 1, humidityLine.c_str());
  }
}
BLYNK_WRITE(LCD_STATS_VIRTUAL)
{
  if (param.asInt() > 0)
  {
    if (!lcdSetByProject) lcdSetByProject = true;
    String firstLine = "GP0: ";
    if (digitalRead(BUTTON_PIN))
      firstLine += "HIGH";
    else
      firstLine += "LOW";
    String secondLine = "ADC0: " + String(analogRead(A0));
    thLCD.clear(); // Clear the LCD
    thLCD.print(0, 0, firstLine.c_str());
    thLCD.print(0, 1, secondLine.c_str());
  }
}

BLYNK_WRITE(LCD_RUNTIME_VIRTUAL)
{
  if (param.asInt() > 0)
  {
    if (!lcdSetByProject) lcdSetByProject = true;
    String topLine = "RunTime-HH:MM:SS";
    String botLine = "    ";
    float seconds, minutes, hours;
    // Calculate seconds, minutes, hours elapsed, based on millis
    seconds = (float)millis() / 1000;
    minutes = seconds / 60;
    hours = minutes / 60;
    seconds = (int)seconds % 60;
    minutes = (int)minutes % 60;
    // Construct a string indicating run time
    if (hours < 10) botLine += "0"; // Add the leading 0
    botLine += String((int)hours) + ":";
    if (minutes < 10) botLine += "0"; // Add the leading 0
    botLine += String((int)minutes) + ":";
    if (seconds < 10) botLine += "0"; // Add the leading 0
    botLine += String((int)seconds);
    
    thLCD.clear(); // Clear the LCD
    thLCD.print(0, 0, topLine.c_str()); // Print top line
    thLCD.print(0, 1, botLine.c_str()); // Print bottom line
  }
}

/* 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9
 9 Experiment 9: Joystick              9
 9 Widget(s):                          9
 9  - Joystick: ServoPos, V14, 0-255,  9
 9     V15, 0-255, Off, Off            9
 9  - Slider: ServoMax, V16, 0-360     9
 9  - Gauge: ServoAngle, V17, 0-360    9
 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 */

#define SERVO_PIN 15 // Servo attached to pin 15
#define SERVO_MINIMUM 5 // Minimum servo angle
unsigned int servoMax = 180; // Default maximum servo angle
int servoX = 0; // Servo angle x component
int servoY = 0; // Servo angle y component
Servo myServo; // Servo object
bool firstServoRun = true;

BLYNK_WRITE(SERVO_XY_VIRTUAL)
{
  // If it's the first time the servo is set, turn it on
  if (firstServoRun)
  {
    myServo.attach(SERVO_PIN);
    myServo.write(15);
    firstServoRun = false;
  }

  // Read in the servo value:
  int servoXIn = param[0].asInt();
  int servoYIn = param[1].asInt();
  BB_DEBUG("Servo X: " + String(servoXIn));
  BB_DEBUG("Servo Y: " + String(servoYIn));
  servoX = servoXIn - 128; // Center xIn around 0 (+/-128)
  servoY = servoYIn - 128; // Center xIn around 0 (+/-128)

  // Calculate the angle, given x and y components:
  float pos = atan2(servoY, servoX) * 180.0 / PI; // Convert to degrees
  // atan2 will give us an angle +/-180
  if (pos < 0) // Convert it to 0-360:
    pos = 360.0 + pos;

  int servoPos = map(pos, 0, 360, SERVO_MINIMUM, servoMax);
  
  // Write the newly calculated angle to a virtual variable:
  Blynk.virtualWrite(SERVO_ANGLE_VIRUTAL, servoPos);

  // Constrain the angle between min/max:
  myServo.write(servoPos); // And set the servo position
}

BLYNK_WRITE(SERVO_MAX_VIRTUAL)
{
  int sMax = param.asInt();
  BB_DEBUG("Servo Max: " + String(sMax));
  servoMax = constrain(sMax, SERVO_MINIMUM + 1, 360);
  Serial.println("ServoMax: " + String(servoMax));
}

/* 10 10 10 10 10 10 10 10 10 10 10 10 10
 10 Experiment 10: Graph               10
 10 Widget(s):                         10
 10  - Graph: Lux, V18, 0-1023,        10
 10    5s, Line                        10
 10  - Slider: UpdateRate, V19, 0-???  10
 10 10 10 10 10 10 10 10 10 10 10 10 10 */

// TSL2561 Definitions:
#define LUX_ADDRESS 0x39 // I2C address of Lux sensor
bool luxInitialized = false; // Lux sensor initialized flag
unsigned int ms = 1000;  // Integration time (ms)
boolean gain = 0; // Lux sensor gain setting
SFE_TSL2561 light; // Lux sensor object

#define LUX_UPDATE_RATE 250 // Lux update rate (ms)
unsigned long lastLuxUpdate = 0; // Last lux update (ms)

void luxInit(void)
{
  // Initialize the SFE_TSL2561 library
  // You can pass nothing to light.begin() for the default I2C address (0x39)
  light.begin();
  
  // If gain = false (0), device is set to low gain (1X)
  gain = 0;
  
  unsigned char time = 0;
  // setTiming() will set the third parameter (ms) to the 13.7ms
  light.setTiming(gain,time,ms);

  // To start taking measurements, power up the sensor:
  light.setPowerUp();
  
  luxInitialized = true;
}

void luxUpdate(void)
{
  if (luxInitialized)
  {
    // This sketch uses the TSL2561's built-in integration timer.
    delay(ms);
    
    // Once integration is complete, we'll retrieve the data.
    unsigned int data0, data1;
    
    if (light.getData(data0,data1))
    {
      double lux;    // Resulting lux value
      boolean good;  // True if neither sensor is saturated
      good = light.getLux(gain,ms,data0,data1,lux);
      BB_DEBUG("Lux: " + String(lux));
      Blynk.virtualWrite(LUX_VIRTUAL, lux);
    }
  }
  else
  {
    int lightADC = analogRead(A0);
    Blynk.virtualWrite(LUX_VIRTUAL, lightADC);
  }
}

/* 11 11 11 11 11 11 11 11 11 11 11 11 11
 11 Experiment 11: History Graph       11
 11 Widget(s):                         11
 11  - History Graph: V20, Voltage     11
 11  - Value: Voltage, V20, 1sec       11
 11 11 11 11 11 11 11 11 11 11 11 11 11 */
BLYNK_READ(ADC_BATT_VIRTUAL)
{
  int rawADC = analogRead(A0);
  float voltage = ((float) rawADC / 1024.0) * ADC_VOLTAGE_DIVIDER;
  voltage *= 2.0; // Assume dividing VIN by two with another divider

  Blynk.virtualWrite(ADC_BATT_VIRTUAL, voltage);
}

/* 12 12 12 12 12 12 12 12 12 12 12 12 12
 12 Experiment 12: Terminal            12
 12 Widget(s):                         12
 12  - Terminal: V21, On, On           12
 12 12 12 12 12 12 12 12 12 12 12 12 12 */
String emailAddress = "";
String boardName = "BlynkMe";

WidgetTerminal terminal(SERIAL_VIRTUAL);

BLYNK_WRITE(SERIAL_VIRTUAL)
{
  String incoming = param.asStr();
  Serial.println(incoming);
  
  if (incoming.charAt(0) == '!')
  {
    String emailAdd = incoming.substring(1, incoming.length());
    for (int i=0; i<emailAdd.length(); i++)
    {
      if (emailAdd.charAt(i) == ' ')
        emailAdd.remove(i, 1);
    }
    terminal.println("Your email is:" + emailAdd + ".");
    emailAddress = emailAdd;
    terminal.flush();
  }
  if (incoming.charAt(0) == '$')
  {
    String newName = incoming.substring(1, incoming.length());

    boardName = newName;
    terminal.println("Board name set to: " + boardName + ".");
    terminal.flush();
  }
}

/* 13 13 13 13 13 13 13 13 13 13 13 13 13
 13 Experiment 13: Twitter             13
 13 Widget(s):                         13
 13  - Twitter: Connect account        13
 13  - Button: TweeEn, V22, Switch     13
 13  - Slider: Threshold, V23, 1023    13
 13  - Slider: Rate, V24, 0-60         13
 13 13 13 13 13 13 13 13 13 13 13 13 13 */
// Tweets are sent in blynkLoop. These functions set enable
// flags and other twitter-controlling parameters.
unsigned long tweetUpdateRate = 60000; // Default tweet rate (ms)
unsigned long lastTweetUpdate = 0; // Last tweet flag
unsigned int moistureThreshold = 512; // Low-moisture setting

BLYNK_WRITE(TWITTER_THRESHOLD_VIRTUAL)
{
  moistureThreshold = param.asInt();
  BB_DEBUG("Tweet threshold set to: " + String(moistureThreshold));
}

BLYNK_WRITE(TWITTER_RATE_VIRTUAL)
{
  int tweetRate = param.asInt();
  if (tweetRate <= 0) tweetRate = 1;
  BB_DEBUG("Setting tweet rate to " + String(tweetRate) + " minutes");
  tweetUpdateRate = tweetRate * 60 * 1000;
}

bool twitterUpdate(void)
{
  unsigned int moisture = analogRead(A0);
  if (moisture < moistureThreshold)
  {
    String msg = boardName + " thirsty!\r\nSoil reading: " + String(moisture) + "\r\n";
    msg += "[" + String(millis()) + "]";
    BB_DEBUG("Tweeting: " + msg);
    Blynk.tweet(msg); 
    return true;
  }
  return false;
}

/* 14 14 14 14 14 14 14 14 14 14 14 14 14
 14 Experiment 14: Push                14
 14 Widget(s):                         14
 14  - Push: Off, On (iPhone)          14
 14  - Value: DoorState, V25, 1sec     14
 14  - Button: PushEnable, V26, Switch 14
 14 14 14 14 14 14 14 14 14 14 14 14 14 */
#define DOOR_SWITCH_PIN 16
#define NOTIFICATION_LIMIT 60000
unsigned long lastDoorSwitchNotification = 0;
uint8_t lastSwitchState = 255;

BLYNK_READ(DOOR_STATE_VIRTUAL)
{
  uint8_t switchState = digitalRead(DOOR_SWITCH_PIN); // Read the door switch pin
  // Pin 16 is pulled low internally. If the switch (and door) is open,
  // pin 16 is LOW. If the switch is closed (door too), pin 16 is HIGH.
  // LOW = open
  // HIGH = closed
  if (switchState)
    Blynk.virtualWrite(DOOR_STATE_VIRTUAL, "Close"); // Update virtual variable
  else
    Blynk.virtualWrite(DOOR_STATE_VIRTUAL, "Open");
    
  if (lastSwitchState != switchState) // If the state has changed
  {
    if (switchState) // If the switch is closed (door shut)
    {
      BB_DEBUG("Notified closed.");
      
      if (lastDoorSwitchNotification && (lastDoorSwitchNotification + NOTIFICATION_LIMIT > millis()))
      {
        int timeLeft = (lastDoorSwitchNotification + NOTIFICATION_LIMIT - millis()) / 1000;
        BB_DEBUG("Can't notify for " + String(timeLeft) + "s");
        terminal.println("Door closed. Can't notify for " + String(timeLeft) + "s");
        terminal.flush();
      }
      else
      {
        Blynk.notify("Door closed\r\nFrom: " + boardName + "\r\n[" + String(millis()) + "]");
        terminal.println("Door closed!");
        terminal.flush();
        lastDoorSwitchNotification = millis();
      }
    }
    else
    { 
      BB_DEBUG("Notified opened.");
      // Send the notification
      if (lastDoorSwitchNotification && (lastDoorSwitchNotification + NOTIFICATION_LIMIT > millis()))
      {
        int timeLeft = (lastDoorSwitchNotification + NOTIFICATION_LIMIT - millis()) / 1000;
        BB_DEBUG("Can't notify for " + String(timeLeft) + "s");
        terminal.println("Door open. Can't notify for " + String(timeLeft) + "s");
        terminal.flush();
      }
      else
      {
        Blynk.notify("Door open\r\nFrom: " + boardName + "\r\n[" + String(millis()) + "]");
        terminal.println("Door opened!");
        terminal.flush();
        lastDoorSwitchNotification = millis();
      }
    }
    lastSwitchState = switchState;
  }  
}

/* 15 15 15 15 15 15 15 15 15 15 15 15 15
 15 Experiment 15: Email               15
 15 Widget(s):                         15
 15  - Email: Off, On (iPhone)         15
 15  - Terminal: V21, On, On           15
 15  - Button: Send, V27, Push         15
 15 15 15 15 15 15 15 15 15 15 15 15 15 */

#define EMAIL_UPDATE_RATE 60000 // Minimum time between emails
unsigned long lastEmailUpdate = 0; // Keeps track of last email send time

void emailUpdate(void)
{
  String emailSubject = "My BlynkBoard Statistics"; // Set the subject
  String emailMessage = ""; // Create a message string
  emailMessage += "D0: " + String(digitalRead(0)) + "\r\n"; // Add D0 status
  emailMessage += "D16: " + String(digitalRead(16)) + "\r\n"; // Add D16 status 
  emailMessage += "\r\n"; // Empty line
  emailMessage += "A0: " + String(analogRead(A0)) + "\r\n"; // Add A0 reading
  emailMessage += "\r\n"; // Empty line
  emailMessage += "Temp: " + String(thSense.readTemperature()) + "C\r\n"; // Add temp sensor
  emailMessage += "Humidity: " + String(thSense.readHumidity()) + "%\r\n"; // Add humidity sensor
  emailMessage += "\r\n"; // Empty line
  emailMessage += "Runtime: " + String(millis() / 1000) + "s\r\n";
  // May have been running into an issue with a too-long emailMessage.
  // Be careful adding anything else to this String.
  BB_DEBUG("email: " + emailAddress);
  BB_DEBUG("subject: " + emailSubject);
  BB_DEBUG("message: " + emailMessage);
  // Send the email:
  Blynk.email(emailAddress.c_str(), emailSubject.c_str(), emailMessage.c_str());
  // Print a help message
  terminal.println("Sent an email to " + emailAddress);
  terminal.flush();
}

BLYNK_WRITE(EMAIL_ENABLED_VIRTUAL)
{
  int emailEnableIn = param.asInt(); // Read parameter in
  BB_DEBUG("Email enabled: " + String(emailEnableIn))
  if (emailEnableIn) // If parameter is >= 1
  {
    // And if an email address has been set through terminal
    if (emailAddress != "") 
    {
      // And if it's been 60 or more seconds since the last email.
      if ((lastEmailUpdate == 0) || (lastEmailUpdate + EMAIL_UPDATE_RATE < millis()))
      { 
        emailUpdate(); // Send an email
        lastEmailUpdate = millis(); // Update the email time
      }
      else // If we haven't waited long enough
      {
        // Print how many seconds before the next print
        int waitTime = (lastEmailUpdate + EMAIL_UPDATE_RATE) - millis();
        waitTime /= 1000;
        terminal.println("Please wait " + String(waitTime) + " seconds");
        terminal.flush();
      }
    }
    else // If an email address has not been set
    { // Print a help message:
      terminal.println("Type !email@address.com to set the email address");
      terminal.flush();
    }
  }
}

// Runtime tracker utility function. Displays the run time to a 
// maximum of four digits. It'll show up to 999 seconds, then
// up to 999 minutes, then up to 999 hours, then up to 999 days
BLYNK_READ(RUNTIME_VIRTUAL)
{
  float runTime = (float) millis() / 1000.0; // Convert millis to seconds
  // Assume we can only show 4 digits
  if (runTime >= 1000) // 1000 seconds = 16.67 minutes
  {
    runTime /= 60.0; // Convert to minutes
    if (runTime >= 1000) // 1000 minutes = 16.67 hours
    {
      runTime /= 60.0; // Convert to hours
      if (runTime >= 1000) // 1000 hours = 41.67 days
        runTime /= 24.0;
    }
  }
  Blynk.virtualWrite(RUNTIME_VIRTUAL, runTime);
}

// Reset WiFi and Blynk auth token 
// Utility function. 
BLYNK_WRITE(RESET_VIRTUAL)
{
  int resetIn = param.asInt();
  if (resetIn)
  {
    BB_DEBUG("Factory resetting");
    resetEEPROM();
    ESP.reset();
  }
}

void blynkSetup(void)
{
  BB_PRINT("Initializing Blynk Board Projects");
  runMode = MODE_BLYNK_RUN; // Set to Blynk Run mode
  
  WiFi.enableAP(false); // Disable access point mode

  // Setup the Pin 0 button:
  detachInterrupt(BUTTON_PIN); // detatch the buttonChange interrupt [BlynkBoard_Core_Firmware]

  // Set up the temperature-humidity sensor
  thSense.begin();

  // Set up the pin 16 door switch input:
  pinMode(DOOR_SWITCH_PIN, INPUT_PULLDOWN_16);
  lastSwitchState = digitalRead(DOOR_SWITCH_PIN);

  if (scanI2C(LUX_ADDRESS)) // Look for a TSL light sensor
  {
    BB_DEBUG("Luminosity sensor connected.");
    luxInit(); // If it's there, initialize it
  }

  BB_DEBUG("Done initializing Blynk demo");
}

void blynkLoop(void)
{
  // Polling Button status -- interrupts lead to bounce errors,
  // especially if noisy buttons are connected.
  if (lastButtonUpdate + BUTTON_UPDATE_RATE < millis())
  {
    buttonUpdate();
    lastButtonUpdate = millis();
  }

  // Polling Light status -- results in the best UX using history graph
  if (lastLuxUpdate + LUX_UPDATE_RATE < millis())
  {
    luxUpdate();
    lastLuxUpdate = millis();
  }

  // If twitter is enabled, and it's been long enough since the last tweet
  if ((lastTweetUpdate == 0) || (lastTweetUpdate + tweetUpdateRate < millis()))
  {
    if (twitterUpdate()) // Send a tweet
      lastTweetUpdate = millis(); // Update the last tweet time if tweet successful
  }

  if (!lcdSetByProject)
  {
    if (lastLCDSplashUpdate + LCD_SPLASH_UPDATE_RATE < millis())
    {
      thLCD.print(0, 0, "sfe.io/blynk    ");
      thLCD.print(0, 1, "       for more!");
  
      lastLCDSplashUpdate = millis();
    }
  }

  if (Serial.available()) // If serial is available
  {
    String toSend;
    while (Serial.available())
      toSend += (char)Serial.read(); // Read all available chars into a string
    terminal.print(toSend); // Send them to the terminal
    terminal.flush(); // Make sure they're sent
  }
}

// Check for a response from an I2C device
bool scanI2C(uint8_t address)
{
  Wire.beginTransmission(address);
  Wire.write( (byte)0x00 );
  if (Wire.endTransmission() == 0)
    return true;
  return false;
}

They (Sparkfun) may not have updated their firmware or example sketches?

I don’t have such a board, but I loaded it up in my Arduino IDE to test; After adding in these libraries (as shown in the Sketch Builder for the Sparkfun Blynk Board):

#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>

It compiled fine for that original issue, however my test now shows ‘BB_DEBUG’ was not declared in this scope

Of which a Google search shows references right back to Sparkfun firmware… GitHub - sparkfun/Blynk_Board_ESP8266: ESP8266-based, Blynk-compatible, beginner-friendly programmable WiFi development board.… So something seems to still be missing (at least on my test).

Give those other two libraries a try on your setup.

Thanks for the help. Unfortunately when I run that code I get a lot of error messages:

Arduino: 1.8.2 (Windows 10), Board: "SparkFun Blynk Board, 80 MHz, Serial, 115200, 4M (1M SPIFFS)"

sketch_jul17a:16: error: stray '\360' in program

 📋 copy

 ^

sketch_jul17a:16: error: stray '\237' in program

sketch_jul17a:16: error: stray '\223' in program

sketch_jul17a:16: error: stray '\213' in program

sketch_jul17a:18: error: stray '\342' in program

 Some sketches may contain errors. Please check your code carefully and âš  report a problem

 ^

sketch_jul17a:18: error: stray '\232' in program

sketch_jul17a:18: error: stray '\240' in program

sketch_jul17a:1: error: 'Blynk' does not name a type

 Blynk

 ^

In file included from C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFi.h:34:0,

                 from C:\Users\matth\Desktop\sketch_jul17a\sketch_jul17a.ino:49:

C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFiSTA.h:38:9: error: 'wl_status_t' does not name a type

         wl_status_t begin(const char* ssid, const char *passphrase = NULL, int32_t channel = 0, const uint8_t* bssid = NULL, bool connect = true);

         ^

In file included from C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFi.h:34:0,

                 from C:\Users\matth\Desktop\sketch_jul17a\sketch_jul17a.ino:49:

C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFiSTA.h:39:9: error: 'wl_status_t' does not name a type

         wl_status_t begin(char* ssid, char *passphrase = NULL, int32_t channel = 0, const uint8_t* bssid = NULL, bool connect = true);

         ^

C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFiSTA.h:40:9: error: 'wl_status_t' does not name a type

         wl_status_t begin();

         ^

C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\ESP8266WiFi\src/ESP8266WiFiSTA.h:72:9: error: 'wl_status_t' does not name a type

         wl_status_t status();

         ^

In file included from C:\Users\matth\Desktop\sketch_jul17a\sketch_jul17a.ino:50:0:

C:\Users\matth\Documents\Arduino\libraries\Blynk\src/BlynkSimpleEsp8266.h: In member function 'void BlynkWifi::connectWiFi(const char*, const char*)':

C:\Users\matth\Documents\Arduino\libraries\Blynk\src/BlynkSimpleEsp8266.h:37:18: error: 'class ESP8266WiFiClass' has no member named 'begin'

             WiFi.begin(ssid, pass);

                  ^

C:\Users\matth\Documents\Arduino\libraries\Blynk\src/BlynkSimpleEsp8266.h:39:18: error: 'class ESP8266WiFiClass' has no member named 'begin'

             WiFi.begin(ssid);

                  ^

C:\Users\matth\Documents\Arduino\libraries\Blynk\src/BlynkSimpleEsp8266.h:41:21: error: 'class ESP8266WiFiClass' has no member named 'status'

         while (WiFi.status() != WL_CONNECTED) {

                     ^

C:\Users\matth\Documents\Arduino\libraries\Blynk\src/BlynkSimpleEsp8266.h:41:33: error: 'WL_CONNECTED' was not declared in this scope

         while (WiFi.status() != WL_CONNECTED) {

                                 ^

Multiple libraries were found for "BlynkSimpleEsp8266.h"
 Used: C:\Users\matth\Documents\Arduino\libraries\Blynk
 Not used: C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\Blynk
 Not used: C:\Program Files (x86)\Arduino\libraries\Blynk
 Not used: C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\Blynk
 Not used: C:\Program Files (x86)\Arduino\libraries\Blynk
 Not used: C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\Blynk
 Not used: C:\Program Files (x86)\Arduino\libraries\Blynk
 Not used: C:\Users\matth\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.1.0\libraries\Blynk
 Not used: C:\Program Files (x86)\Arduino\libraries\Blynk
exit status 1
stray '\360' in program

This report would have more information with
"Show verbose output during compilation"
option enabled in File -> Preferences.

Maybe I am going about this the wrong way, maybe I don’t need to re-load the sparkfun code.
Is there some code in the Blynk library that will make the Blynk board connect to the Blynk app.
Something like Blynk.broadcast? I just need my android phone and the blynk board to be communicating with each other.

Well, I am still learning about ESP8266 based firmware (Seems to be way too many different versions and ways to install)… but have you tried any of the Sketch Builder options as far as libraries and sketches go?

If you haven’t already, check out that link from my previous post.

I have, still not able to compile. I’ll keep digging around too. This is disappointing that it’s so difficult to reset this board to it’s stock condition.

I got it!
Ok so it wasn’t all that difficult once I found the right version of files:
It is located in the customer comments area on the sparkfun page: https://www.sparkfun.com/products/13794

You need to download this file:
https://github.com/sparkfun/Blynk_Board_ESP8266/archive/master.zip

Then open the BlynkBoard_Core_Firmware.ino file in Arduino

Upload the main firmware, then upload the config “tab” within ardunio.

Worked like a charm.

1 Like