Blynk BLE has serious lag with Arduino 101

So, I have an Arduino 101 controlling a robot (similar to another project I did with a Particle Photon).

However, while I was able to successfully connect to the A101 with my smartphone Blynk app, commands would be received incredibly slow, and essentially block out any other functions I have on the app. For example, there is a 2-axis joystick mapped to V1 which controls motion, a separate button mapped to V2 which controls an array of WS2812B LED strips, and another button mapped to D13 just to check connectivity.

Any input on the joystick will cause the entire program to lag. Attempting to use either Color or Status button will result in about a 30 second delay. Using the color button seems okay, but if I press it more than two or three times in a row, more lag, to the point where it takes about a minute to catch up.

I don’t have the sketch on my desktop, here, but I’ll post it as soon as I can get it (probably in another five minutes)

Help!

Code as follows:

// This #include statement was automatically added by the Particle IDE.
#define BLINK_SERIAL Serial
#include <BlynkSimpleCurieBLE.h>
#include <CurieBLE.h>


// This #include statement was automatically added by the Particle IDE.
#include <Adafruit_NeoPixel.h>
#define PIXEL_PIN 6
#define PIXEL_COUNT 240
//#define PIXEL_TYPE WS2812B

#define BLYNK_USE_DIRECT_CONNECT



#define StatusPin 13

// #include <SimpleTimer.h>

// SimpleTimer timer;

Adafruit_NeoPixel strip = Adafruit_NeoPixel(PIXEL_COUNT, PIXEL_PIN);

char auth[] = "2b0d690f7e8546afb1fd49d528cdddd4"; // insert Auth Token from Blynk app, here

// Private Blynk Server
/************************************
  //IPAddress server_ip (192,168,0,101);

  //char SSID[] = "**";
  //char pass[] = "**";

*************************************/


// Blynk Bluetooth
BLEPeripheral blePeripheral;



int r_motor = 9;
int l_motor = 11;
//Servo r_motor;
//Servo l_motor;
int lastRmotor = 0;
int lastLmotor = 0;

int status_pin = 13;

int color_state = 0;

char pCloudData[40];

// SYSTEM_MODE(SEMI_AUTOMATIC);

int timeoutCnt = 0;

void setup() {

  pinMode(StatusPin, OUTPUT);

  Serial.begin(115200);
  pinMode(r_motor, OUTPUT);
  pinMode(l_motor, OUTPUT);
  //  pinMode(status_pin, OUTPUT);
  //    r_motor.attach(10);
  //    l_motor.attach(11);

  delay(2000);
  /*********** Blynk Wifi Initialization ************/
  //    WiFi.setCredentials(SSID, pass);
  //    WiFi.connect();
  //    timeoutCnt = 0;
  //    while(WiFi.connecting() && timeoutCnt <= 60000)
  //        timeoutCnt = timeoutCnt + 1;

  /*********** Blynk Bluetooth Initialization ********/
  blePeripheral.setLocalName("**");
  blePeripheral.setDeviceName("**");
  blePeripheral.setAppearance(384);


  //    Blynk.begin(auth, server_ip, 8442);

  Blynk.begin(auth, blePeripheral);

  blePeripheral.begin();
  //    while(Blynk.connect()== false)
  //    {
  //        digitalWrite(StatusPin, HIGH);
  //        delay(100);
  //        digitalWrite(StatusPin, LOW);
  //        delay(100);
  //        digitalWrite(StatusPin, HIGH);
  //        delay(100);
  //        digitalWrite(StatusPin, LOW);
  //        delay(500);
  //
  //    }

  //  // Status Pin setup
  //  digitalWrite(StatusPin, HIGH);
  //  delay(100);
  //  digitalWrite(StatusPin, LOW);
  //  delay(100);
  //  digitalWrite(StatusPin, HIGH);
  //  delay(100);
  //  digitalWrite(StatusPin, LOW);
  //  delay(500);

  //    if(Blynk.connect())
  //    {
  //        digitalWrite(StatusPin, LOW);
  //    }

  // try this
  // Blynk.begin(auth);
  // Initialize all pixels to "off"
  strip.begin();
  strip.show();
}

// Joystick widget, use the 2-axis joystick with merged outputs
BLYNK_WRITE(V1) {
  int x = param[0].asInt();
  int y = param[1].asInt();

  //    sprintf(pCloudData, "X: %d, Y: %d", x,y);
  //    Particle.publish("detected joystick input", pCloudData);
  // Particle.publish("X axis: ", x);
  // Particle.publish("Y axis: ", y);
  Serial.print("X = ");
  Serial.println(x);
  Serial.print("Y = ");
  Serial.println(y);

  Arcade(x, y);
}

// RGB Widget: Use ZeRGBa widget on the app
BLYNK_WRITE(V2) {
  color_state = color_state + param[0].asInt();
  int red = 0;
  int green = 0;
  int blue = 0;
  //    sprintf(pCloudData, "R: %d, G: %d, B: %d", r,g,b);
  //    Particle.publish("detected RGB input", pCloudData);
  if (color_state > 16)
  {
    color_state = 1;
  }

  switch (color_state) {
    case 1 : red = 255; green = 0; blue = 0;
      Serial.println("Color mode 1");
      break;
    case 2 : red = 0; green = 255; blue = 0;
    Serial.println("Color mode 2");
      break;
    case 3 : red = 0; green = 0; blue = 255;
    Serial.println("Color mode 3");
      break;
    case 4 : red = 0; green = 255; blue = 255;
    Serial.println("Color mode 4");
      break;
    case 5 : red = 255; green = 255; blue = 0;
    Serial.println("Color mode 5");
      break;
    case 6 : red = 255; green = 0; blue = 255;
    Serial.println("Color mode 6");
      break;
    case 7 : red = 255; green = 20; blue = 147;
    Serial.println("Color mode 7");
      break;
    case 8 : red = 139; green = 0; blue = 139;
    Serial.println("Color mode 8");
      break;
    case 9 : red = 75; green = 0; blue = 130;
    Serial.println("Color mode 9");
      break;
    case 10 : red = 0; green = 245; blue = 255;
    Serial.println("Color mode 10");
      break;
    case 11 : red = 0; green = 250; blue = 155;
    Serial.println("Color mode 11");
      break;
    case 12 : red = 0; green = 201; blue = 87;
    Serial.println("Color mode 12");
      break;
    case 13: red = 218; green = 165; blue = 32;
    Serial.println("Color mode 13");
      break;
    case 14 : red = 255; green = 165; blue = 0;
    Serial.println("Color mode 14");
      break;
    case 15 : red = 255; green = 69; blue = 0;
    Serial.println("Color mode 15");
      break;
    case 16 : red = 255; green = 140; blue = 105;
    Serial.println("Color mode 16");
      break;
    default : red = 0; green = 0; blue = 0;
    Serial.println("Color mode Default");
      break;
  }

  for (int i = 0; i < strip.numPixels(); i++) {
    strip.setPixelColor(i, red, green, blue);
    strip.show();
  }
  //     sprintf(pCloudData, "R: %d, G: %d, B: %d", red, green, blue);
  // Particle.publish("detected RGB input", pCloudData);

  //        delay(20);
}


void loop() {

  //rainbow(20);
  // rampUp(r_motor, 255,0);
  // rampDn(r_motor, 0,255);
  // rampUp(l_motor, 255,0);
  // rampDn(l_motor, 0, 255);
  //    if(WiFi.ready()==false)
  //        Particle.connect();
  Blynk.run();
  blePeripheral.poll();

}

void rainbow(uint8_t wait) {
  uint16_t i, j;

  for (j = 0; j < 256; j++) {
    for (i = 0; i < strip.numPixels(); i++) {
      strip.setPixelColor(i, Wheel((i + j) & 255));
    }
    strip.show();
    //    delay(wait);
  }
}

// Input a value 0 to 255 to get a color value.
// The colours are a transition r - g - b - back to r.
uint32_t Wheel(byte WheelPos) {
  if (WheelPos < 85) {
    return strip.Color(WheelPos * 3, 255 - WheelPos * 3, 0);
  } else if (WheelPos < 170) {
    WheelPos -= 85;
    return strip.Color(255 - WheelPos * 3, 0, WheelPos * 3);
  } else {
    WheelPos -= 170;
    return strip.Color(0, WheelPos * 3, 255 - WheelPos * 3);
  }
}

void Arcade(int x, int y) // make joystick arcade style controller
{
  int powY;
  int powX;
  int powRightMotor;
  int powLeftMotor;

  // convert joystick 0 - 255 range to -100 to 100 for powering motors
  //   powY = ((y - 127)* 100) / 127;         // joystick y axis gives maximum power level
  //   powX = ((x - 127)* 100) / 127;         // x axis determines which motor is reduced or
  // reversed for a turn
  powY = y / 100;
  powX = x / 100;
  // sprintf(pCloudData, "X: %d, Y: %d", powX, powY);
  //Particle.publish("Arcade Values", pCloudData);

  if (powX < 75) //  if x negative, turning left; otherwise, turning right
  {
    powLeftMotor = (powY * (powX / 100)); // left motor reduced for Left turn
    powRightMotor = powY;                           // right motor not changed
  }
  else if (powX > 125)
  {
    powRightMotor = (powY * ((100 - (powX  / 2)) / 100)); // right motor reduced for Right turn
    powLeftMotor = powY;                            // left motor not changed
  }
  else
  {
    powRightMotor = powY;
    powLeftMotor = powY;
  }

  if (powRightMotor >= lastRmotor)
    rampUp(r_motor, powRightMotor, lastRmotor);
  else
    rampDn(r_motor, powRightMotor, lastRmotor);
  if (powLeftMotor >= lastLmotor)
    rampUp(l_motor, powLeftMotor, lastLmotor);
  else
    rampDn(l_motor, powLeftMotor, lastLmotor);

  lastRmotor = powRightMotor;
  lastLmotor = powLeftMotor;
  // r_motor.write(powRightMotor);
  // l_motor.write(powLeftMotor);
}

void rampUp(int thisMotor, int mtrPwr, int strtPwr)
{
  for (int x = strtPwr; x < mtrPwr;) {
    analogWrite(x, thisMotor);
    x = x + 5;
    delay(10);
  }
}

void rampDn(int thisMotor, int mtrPwr, int strtPwr) {
  for (int x = strtPwr; x > mtrPwr;) {
    analogWrite(x, thisMotor);
    x = x - 5;
    delay(10);
  }
}

Not sure about your BLE issue, but I’d recommend changing to the fastLED library to control your LED’s… far simpler and faster.

Then you could do something like this:

#include <FastLED.h>

#define DATA_PIN           6 // LED control pin
#define NUM_LEDS           240 // Number of LEDs

int varHue;

CRGB leds[NUM_LEDS];

void setup(){
  FastLED.addLeds<WS2811B, DATA_PIN, GRB>(leds, NUM_LEDS);
}
  

// set up a slider instead of a ZeRGBa widget
BLYNK_WRITE(V2)
{
  varHue = param.asInt();
  Serial.print("Hue: ");
  Serial.println(varHue);
  Serial.flush();

}

void loop(){
   fill_solid(leds, NUM_LEDS, CHSV(varHue, 255, 255)); // set up saturation/brightness sliders too if you want.
   FastLED.show();
}

Also for code:

1 Like

Update the code.

Thanks!

Yeah I just have a feeling the way you put the strip.show(); in the BLYNK_WRITE function will cause some loop errors and is probably why you are getting major delays.

1 Like

It might be an issue, sure (one of many).

This does work without issue on a WiFi enabled arduino, though (the Particle Photon, to be exact)

Ahh okay… personally I have not tried the BLE part of Blynk.
Hopefully one of the devs will be able to help :slight_smile:

1 Like