Fix motor code - use abs speed

Fix motor code - use abs speed

--- testing/arduino/self-driving-v6.ino
+++ testing/arduino/self-driving-v6.ino
@@ -159,18 +159,19 @@

 void SetMotorWorker(int pin1, int pin2, int enablePin, int speed)
 {
+    analogWrite(enablePin, abs(speed));
+
     if (speed < 0)
     {
         analogWrite(pin1, 0);
         analogWrite(pin2, 255);
     }
-    else
+
+    if (speed > 0)
     {
         analogWrite(pin1, 255);
         analogWrite(pin2, 0);
     }
-
-    analogWrite(enablePin, speed);

     if (speed == 0)
     {


Fixed some bugs with the moving.

Fixed some bugs with the moving.

--- firmware/firmware.ino
+++ firmware/firmware.ino
@@ -11,7 +11,7 @@
 #define PIN_MOTOR_B_INPUT_1 30
 #define PIN_MOTOR_B_INPUT_2 32

-const int motor_speed_max = 200;
+const int motor_speed_max = 240;
 int motor_speed_now = 0;
 String input_buffer = "";

@@ -81,19 +81,19 @@

     if (input_buffer.length()) {
       int last_char = input_buffer.indexOf('&');
-      if (last_char != -1) {
+      while (last_char != -1) {
         switch (input_buffer[0]) {
           case '1': //moveTo
           case '3': //moveToByTime
             {
-              moving_time = input_buffer.substring(2, last_char - 1).toInt();
+              moving_time = input_buffer.substring(2, last_char).toInt();
               robotMove(input_buffer[1] == '1');
             }
             break;
           case '2': //rotateTo
           case '4': //rotateToByTime
             {
-              moving_time = input_buffer.substring(2, last_char - 1).toInt();
+              moving_time = input_buffer.substring(2, last_char).toInt();
               robotRotate(input_buffer[1] == '1');
             }
             break;
@@ -102,7 +102,7 @@
               int intensity = map(input_buffer.substring(2, 4).toInt(), 0, 100, 0, 255);
               int period;
               if (intensity) {
-                period = input_buffer.substring(5, last_char - 1).toInt();
+                period = input_buffer.substring(5, last_char).toInt();
               } else {
                 period = 0;
               }
@@ -191,7 +191,8 @@
             }
             break;
         }
-        input_buffer.remove(0, last_char + 1);
+        input_buffer.remove(0, last_char + 1);
+        last_char = input_buffer.indexOf('&');
       }
     }
   }
@@ -199,7 +200,7 @@
   if (is_moving) {
     if (is_acceleration) {
       current_millis = millis();
-      if (current_millis - previous_millis_accelarting > 30) {
+      if (current_millis - previous_millis_accelarting > 10) {
         previous_millis_accelarting = current_millis;

         motor_speed_now++;
@@ -268,6 +269,7 @@
   is_moving = true;
   is_rotation = false;
   is_forward = forward;
+  previous_millis_moving = millis();
 }
 void robotRotate(bool right){
   if (right) {
@@ -283,6 +285,7 @@
   is_moving = true;
   is_rotation = true;
   is_forward = right;
+  previous_millis_moving = millis();
 }
 void robotStop(){
   analogWrite(PIN_MOTOR_A_ENABLE, 0);


moved

moved

--- Arduino/serial_led.ino
+++ Arduino/serial_led.ino
@@ -1,929 +0,0 @@
- /***********************************************************************
- *  Copyright (c) 2014 - Matthew Fatheree <greymattr@gmail.com>
- *  All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- *    notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *    notice, this list of conditions and the following disclaimer in the
- *    documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES.  THE USER(S) ARE HEREBY NOTIFIED THAT USE OF THIS SOFTWARE MAY
- * MAY CAUSE LOSS OF DATA, DATA DESTRUCTION, HEALTH AND MENTAL PROBLEMS. IT
- * MAY CAUSE YOU TO START DRINKING, INCREASE YOUR STUPIDITY LEVEL, CLUB
- * BABY SEALS, AND OVERALL BECOME A BAD PERSON.
- *
- * PLEASE USE AT YOUR OWN RISK
- * ____    ________
- * \   \  /    ___/
- * |    \/     __|
- * |  |\__/|  |
- * /  \atthew \atheree
- ************************************************************************/
-
-#include <stdarg.h>
-
-#define	min(a,b)	  ((a) < (b) ? (a) : (b))
-#define	max(a,b)	  ((a) > (b) ? (a) : (b))
-
-#define SET_BIT(p,n)      ((p) |= (1 << (n)))
-#define CLR_BIT(p,n)      ((p) &= (~(1) << (n)))
-#define IS_BIT_SET(val, bit_no) (((val) >> (bit_no)) & 1)
-
-#define INTENSE_MIN        0
-#define INTENSE_MAX        255
-
-
-//#define FADE_STEPS         8
-#define FADE_STEPS         16
-//#define FADE_STEPS         32
-
-#define SL_VERSION         "v0.1.1"
-
-
-
-#define BORDER             "\n--------------------\n"
-#define LED_CHOICE         "Which LED would you like to"
-#define FREQ_CHOICE        "How quickly would you like it to"
-#define REPEAT_CHOICE      "How many times should it"
-#define INTENSE_CHOICE     "How bright"
-#define MODE_SEL_ERR       "mode select error\n"
-#define PARAM_ERR          "parameter error\n"
-
-#define HIGH_VAL_STR       "High Value"
-#define MID_VAL_STR        "Mid Value"
-#define LOW_VAL_STR        "Low Value"
-
-#define CONTROL_SETTINGS   "Control Settings"
-#define START_INTS         "Start Intensity"
-#define END_INTS           "End Intensity"
-#define TXT_MACRO          "\n\n macro = "
-
-
-#define MAX_MACRO_LEN      128
-#define SMALL_BUFF         8
-
-#define LED1_FLAG          1
-#define LED2_FLAG          2
-#define LED3_FLAG          4
-#define LED4_FLAG          8
-#define LED5_FLAG          16
-#define LED6_FLAG          32
-#define LED7_FLAG          64
-#define LED8_FLAG          128
-#define LED9_FLAG          256
-#define LED10_FLAG         512
-#define LED11_FLAG         1024
-#define LED12_FLAG         2048
-#define LED13_FLAG         4096
-
-//macro modes
-#define MODE_BLINK         1
-#define MODE_PULSE         2
-#define MODE_FADE          3
-#define MODE_WAIT          4
-#define MODE_SET           5
-
-#define MAX_LEDS           13
-#define ALL_LEDS           8191
-#define NONE_LEDS          0
-
-#define POWER_SAVE
-
-int HighVal = INTENSE_MAX;
-int MidVal = INTENSE_MAX / 2;
-int LowVal = INTENSE_MIN;
-int UserLed = 10;
-int UserVal = INTENSE_MAX;
-int UserFreq = 1000;
-int UserRepeat = 1;
-int UserState1 = LowVal;
-int UserState2 = HighVal;
-char Uinput[ MAX_MACRO_LEN ];
-
-void setup()
-{
-  int x = 0;
-
-  for( x=0; x<=MAX_LEDS; x++ ) {
-    pinMode( UserLed,OUTPUT );    // Configure the onboard LED for output
-    analogWrite( UserLed,0 );  // default to LED off
-  }
-  Serial.begin( 57600 );
-  while( !Serial ) {
-    delay( 500 );
-  }
-  delay( 1000 ); // because Arduino,... am I right?...
-
-}
-
-void p( char *fmt, ... )
-{
-  char buf[MAX_MACRO_LEN]; // resulting string limited to 128 chars
-  va_list args;
-  va_start ( args, fmt );
-  memset( buf, 0, sizeof( buf ) );
-  vsnprintf( buf, MAX_MACRO_LEN, fmt, args );
-  va_end ( args );
-  Serial.print( buf );
-}
-
-void display_menu()
-{
-  delay( 500 );
-  p( "\n\n    LED %s %s\n", CONTROL_SETTINGS, SL_VERSION );
-  p( " I. Intensity %s\n", CONTROL_SETTINGS );
-  p( " F. Fade  %s\n", CONTROL_SETTINGS );
-  p( " P. Pulse %s\n", CONTROL_SETTINGS );
-  p( " B. Blink %s\n", CONTROL_SETTINGS );
-  p( " C. Clear all LEDS off\n" );
-#if 0
-  p( " M. Macro %s\n", CONTROL_SETTINGS );
-#endif
-  p( "%s", BORDER);
-  p( " > " );
-}
-
-void loop()
-{
-  char *selection;
-  int a = 0;
-  int ok;
-
-  display_menu();
-  selection = get_user_input();
-  memset( Uinput, 0, sizeof( Uinput ) );
-  for( a=0; a<( MAX_MACRO_LEN-1 ); a++ ) {
-    Uinput[a] = ( char ) *( selection + a );
-    if( Uinput[a] == '\0' ) {
-      break;
-    }
-  }
-  switch ( Uinput[0] ) {
-  case 'I':
-  case 'i':
-    IntensityControls();
-    break;
-  case 'F':
-  case 'f':
-    FadeControls();
-    break;
-  case 'P':
-  case 'p':
-    PulseControls();
-    break;
-  case 'B':
-  case 'b':
-    BlinkControls();
-    break;
-  case 'C':
-  case 'c':
-    p( "\n All LEDS OFF\n\n" );
-    a = 8191;
-    p("%s c\n", TXT_MACRO);
-    set_leds( a, 0 );
-    break;
-  case '*':
-    SayHello();
-    break;
-#if 1
-  case 't':
-    // put test functions here
-    unrecognized();
-    break;
-  case 'M':
-  case 'm':
-    //unrecognized();
-    parse_macro( ( char * )( Uinput + 1 ) );
-    break;
-#endif
-  default:
-    unrecognized();
-    break;
-  }
-
-}
-
-
-void set_leds( int leds, int brightness )
-{
-  int x;
-  //p("\nset led(s) %d at %d\n", leds, brightness);
-  for( x=1; x<=MAX_LEDS; x++ ) {
-    if( IS_BIT_SET( leds, x ) ) {
-      analogWrite( x,brightness );
-    }
-  }
-}
-
-void leds_off( int leds )
-{
-  set_leds( leds,0 );
-}
-
-void leds_on( int leds )
-{
-  set_leds( leds,255 );
-}
-
-void blink_leds( int leds, int brightness, int freq, int repeat )
-{
-  int i = 0, x = 0;
-  int led;
-
-  set_leds( leds, 0 );
-  //p( "\n blink led(s) %d at %d/%dms %d times\n", leds, brightness, freq, repeat );
-  for( i=0; i<repeat; i++ ) {
-    set_leds( leds, brightness );
-    delay( freq / 2 );
-    set_leds( leds, 0 );
-    delay( freq/2 );
-  }
-}
-
-void blink_led( int led, int b, int f, int r )
-{
-  int ls = 0;
-  SET_BIT( ls, led );
-  blink_leds( ls, b, f, r );
-}
-
-void fade_leds( int leds, int from, int to, int freq, int repeat )
-{
-  int total_time = freq;
-  int steps = FADE_STEPS;
-  int total_range = ( ( max( from,to ) ) - min( from,to ) );
-  int step_value =  ( total_range / steps );
-  int sleep_value = ( total_time / steps );
-  int i, y;
-  int curval;
-  int led = 0;
-
-  //p( "\n fade led(s) %d from %d to %d/%dms %d times\n", leds, from, to, freq, repeat );
-  for( i=0; i<repeat; i++ ) {
-    curval = from;
-    for ( y=0; y<=steps; y++ ) {
-      if( curval < 0 ) {
-        curval = 0;
-      }
-      set_leds( leds, curval );
-      if( curval > to ) {
-        curval = curval - step_value;
-      } else {
-        curval = curval + step_value;
-      }
-      delay( sleep_value );
-    }
-  }
-  set_leds( leds, to );
-}
-
-void fade_led( int leds, int from, int to, int freq, int repeat )
-{
-  int ls = 0;
-  SET_BIT( ls, leds );
-  fade_leds( ls, from, to, freq, repeat );
-}
-
-
-void pulse_leds( int leds, int from, int to, int freq, int repeat )
-{
-  int i;
-  int new_freq = freq / 2;
-  for( i=0; i<repeat; i++ ) {
-    fade_leds( leds, from, to, new_freq, 1 );
-    fade_leds( leds, to, from, new_freq, 1 );
-  }
-
-}
-
-void pulse_led( int led, int from, int to, int freq, int repeat )
-{
-  int ls = 0;
-  SET_BIT( ls, led );
-  pulse_leds( ls, from, to, freq, repeat );
-}
-
-void SayHello()
-{
-  p( "%s", BORDER );
-  p( "\n Hey Matt... greymattr want a beer?... You're awesome!...\n" );
-  p( "%s", BORDER );
-}
-
-char *get_user_input()
-{
-  int i=0;
-  char b = 0;
-  char commandbuffer[MAX_MACRO_LEN];
-
-  memset( commandbuffer, 0, sizeof( commandbuffer ) );
-  while( i < ( sizeof( commandbuffer )-1 ) ) {
-    if( Serial.available() ) {
-      b = Serial.read();
-      if( b != 0x08 ){
-        commandbuffer[i++] = b;
-      } else {
-        commandbuffer[i] = '\0';
-        i--;
-      }
-      if( ( b == 0x0a ) || ( b== 0x0d ) ) {
-        break;
-      } else {
-        Serial.write( b );
-      }
-    }
-  }
-  if( i<2 ) {
-    return "\0";
-  }
-  commandbuffer[i]='\0';
-  //p("\ncmd buffer = %s\n", commandbuffer);
-  return commandbuffer;
-}
-
-int get_user_int( int orig )
-{
-  char *arg = '\0';
-  int val = 0;
-  arg = get_user_input();
-  if( *arg != '\0' ) {
-    val=atoi( arg );
-    if( ( val >= INTENSE_MIN ) && ( val <= INTENSE_MAX ) ) {
-      return val;
-    } else {
-      return orig;
-    }
-  }
-  return orig;
-}
-
-int get_user_intlarge( int orig )
-{
-  char *arg = '\0';
-  int val = 0;
-  arg = get_user_input();
-  if( *arg != '\0' ) {
-    val=atoi( arg );
-    if( ( val >= 0 ) && ( val <= 0xFFFF ) ) {
-      return val;
-    } else {
-      return orig;
-    }
-  }
-  return orig;
-}
-
-void BlinkControls()
-{
-  int aNumber;
-  char resp;
-  char *arg = '\0';
-  int ok;
-  int val;
-
-  Serial.flush();
-  p( "\n\nBlink %s\n", CONTROL_SETTINGS );
-  p( "%s blink [ %d ]?: ", LED_CHOICE, UserLed );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserLed = get_user_int( UserLed );
-  p( "\n%s blink [ %dms ]?: ", FREQ_CHOICE, UserFreq );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserFreq = get_user_intlarge( UserFreq );
-  p( "\n%s (1-255) [ %d ]?: ", INTENSE_CHOICE, UserVal );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserVal = get_user_int( UserVal );
-  p( "\n%s should it blink [ %d ]?: ", REPEAT_CHOICE, UserRepeat );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserRepeat = get_user_int( UserRepeat );
-  p("%s ml(%d)b(%d,%d,%d)\n", TXT_MACRO,UserLed, UserVal, UserFreq, UserRepeat);
-  blink_led( UserLed, UserVal, UserFreq, UserRepeat );
-}
-
-void IntensityControls()
-{
-  char *arg = NULL;
-  int val = 0;
-  int ok;
-
-  Serial.flush();
-  p( "\n\nIntensity %s ( 1 - 255 )\n", CONTROL_SETTINGS );
-  p( "%s [ %d ]?: ",HIGH_VAL_STR, HighVal );
-  while( !Serial.available() ) {
-    ;
-  }
-  HighVal = get_user_int( HighVal );
-  p( "\n %s [ %d ]?: ",MID_VAL_STR, MidVal );
-  while( !Serial.available() ) {
-    ;
-  }
-  MidVal = get_user_int( MidVal );
-  p( "\n %s [ %d ]?: ",LOW_VAL_STR, LowVal );
-  while( !Serial.available() ) {
-    ;
-  }
-  LowVal = get_user_int( LowVal );
-  p( "%s", BORDER );
-  p( "%s=%d, %s=%d, %s=%d\n",HIGH_VAL_STR,HighVal,MID_VAL_STR, MidVal,LOW_VAL_STR, LowVal );
-  p( "%s", BORDER );
-  p( "\n%s set [ %d ]?: ", LED_CHOICE, UserLed );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserLed = get_user_int( UserLed );
-  p( "\n%s [ %d ]?: ", INTENSE_CHOICE, UserVal );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserVal = get_user_intlarge( UserVal );
-  p( "%s", BORDER );
-  p( "\nLED %d set to %d\n", UserLed, UserVal );
-  p("%s ml(%d)i(%d)\n", TXT_MACRO,UserLed, UserVal);
-  analogWrite( UserLed, UserVal );
-  p( "%s", BORDER );
-}
-
-void intensity_menu()
-{
-  p( "\n a. %s ( %d )\n", HIGH_VAL_STR, HighVal );
-  p( " b.  %s ( %d )\n", MID_VAL_STR, MidVal );
-  p( " c.  %s ( %d )\n", LOW_VAL_STR, LowVal );
-}
-
-void FadeControls()
-{
-  char *arg = '\0';
-  int state1 = UserState1;
-  int state2 = UserState2;
-
-  Serial.flush();
-  p( "\n\nFade %s\n", CONTROL_SETTINGS );
-  p( "%s fade [ %d ]?: ", LED_CHOICE, UserLed );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserLed = get_user_int( UserLed );
-  intensity_menu();
-  p( "%s [ %d ]?: ", START_INTS, UserState1 );
-  while( !Serial.available() ) {
-    ;
-  }
-  arg = get_user_input();
-  switch( *arg ) {
-  case 'A':
-  case 'a':
-    UserState1 = HighVal;
-    break;
-  case 'B':
-  case 'b':
-    UserState1 = MidVal;
-    break;
-  case 'C':
-  case 'c':
-    UserState1 = LowVal;
-    break;
-  default:
-    state1 = atoi( arg );
-    if( ( state1 > 255 ) || ( state1 < 0 ) ) {
-      state1=UserState1;
-    } else {
-      state1 = UserState1;
-    }
-    break;
-  }
-  intensity_menu();
-  p( "%s [ %d ]?: ",END_INTS, UserState2 );
-  while( !Serial.available() ) {
-    ;
-  }
-  arg = get_user_input();
-  switch( *arg ) {
-  case 'A':
-  case 'a':
-    state2 = HighVal;
-    break;
-  case 'B':
-  case 'b':
-    state2 = MidVal;
-    break;
-  case 'c':
-  case 'C':
-    state2 = LowVal;
-    break;
-  default:
-    state2 = atoi( arg );
-    if( ( state2 > 255 ) || ( state2 < 0 ) ) {
-      state2=UserState2;
-    } else {
-      state2 = UserState2;
-    }
-    break;
-  }
-  UserState2 = state2;
-  p( "\n%s fade [ %d ]?: ", FREQ_CHOICE, UserFreq );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserFreq = get_user_intlarge( UserFreq );
-  p( "\n%s fade [ %d ]?: ", REPEAT_CHOICE, UserRepeat );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserRepeat = get_user_int( UserRepeat );
-  p("%s ml(%d)f(%d,%d,%d,%d)\n", TXT_MACRO,UserLed, UserState1, UserState2, UserFreq, UserRepeat);
-  fade_led( UserLed, UserState1, UserState2, UserFreq, UserRepeat );
-}
-
-void PulseControls()
-{
-  char *arg = '\0';
-  int sel = 0;
-  int state1, state2;
-  int ok;
-
-  Serial.flush();
-  p( "\n\nPulse %s\n", CONTROL_SETTINGS );
-  p( "%s Pulse [ %d ]?: ",LED_CHOICE, UserLed );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserLed = get_user_int( UserLed );
-  intensity_menu();
-  p( "%s [ %d ]?: ", START_INTS, UserState1 );
-  while( !Serial.available() ) {
-    ;
-  }
-  arg = get_user_input();
-  switch( arg[0] ) {
-  case 'a':
-  case 'A':
-    state1 = HighVal;
-    break;
-  case 'b':
-  case 'B':
-    state1 = MidVal;
-    break;
-  case 'c':
-  case 'C':
-    state1 = LowVal;
-    break;
-  default:
-    state1 = atoi( arg );
-    if( ( state1 > 255 ) || ( state1 < 0 ) ) {
-      state1=UserState1;
-    } else {
-      state1 = UserState1;
-    }
-    break;
-  }
-  UserState1 = state1;
-  p( "\n%s %d\n", START_INTS, UserState1 );
-  intensity_menu();
-  p( "%s [ %d ]?: ",END_INTS, UserState2 );
-  while( !Serial.available() ) {
-    ;
-  }
-  arg = get_user_input();
-  switch( arg[0] ) {
-  case 'a':
-  case 'A':
-    state2 = HighVal;
-    break;
-  case 'b':
-  case 'B':
-    state2 = MidVal;
-    break;
-  case 'c':
-  case 'C':
-    state2 = LowVal;
-    break;
-  default:
-    state2 = atoi( arg );
-    if( ( state2 > 255 ) || ( state2 < 0 ) ) {
-      state2=UserState2;
-    } else {
-      state2 = UserState2;
-    }
-    break;
-  }
-  UserState2 = state2;
-  p( "\n%s pulse [ %d ]?: ", FREQ_CHOICE, UserFreq );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserFreq=get_user_intlarge( UserFreq );
-  p( "\n%s pulse [ %d ]?: ", REPEAT_CHOICE, UserRepeat );
-  while( !Serial.available() ) {
-    ;
-  }
-  UserRepeat=get_user_int( UserRepeat );
-  p("%s ml(%d)p(%d,%d,%d,%d)\n", TXT_MACRO,UserLed, UserState1, UserState2, UserFreq, UserRepeat);
-  pulse_led( UserLed, UserState1, UserState2, UserFreq, UserRepeat );
-}
-
-int parse_macro( char *macro )
-{
-  int ok = 0;
-  long int leds = 0;
-  char *ch;
-  char buf[ SMALL_BUFF ];
-  int val1 = -1;
-  int val2 = -1;
-  int freq = -1;
-  int repeat = -1;
-  int wait = -1;
-  int state = 0;
-  int i, x;
-  int scratch = 0;
-  int mode = 0;
-
-  set_leds( ALL_LEDS, 0 );
-  p( "\nRun Macro [ %s ]\n", macro-1 );
-  for( i=0; i<( MAX_MACRO_LEN - 1 ); i++ ) {
-    ch = ( char * )( macro + i );
-    switch( *ch ) {
-    case 'l':
-    case 'L':
-      leds = 0;
-      if( *( ch + 1 ) == '(' ) {
-        i++;  // skip char
-        memset( buf, 0, sizeof( buf ) );
-        for( x=0; x<sizeof( buf ); x++ ) {
-          i++;
-          ch = ( char * )( macro + i );
-          switch( *ch ) {
-          case ',':
-          case ')':
-            scratch = atoi( buf );
-            //p("got led #%d\n", scratch);
-            SET_BIT( leds, scratch );
-            if( *ch == ')' ) {
-              for( x=0; x<MAX_LEDS; x++ ) {
-                if( IS_BIT_SET( leds, x ) ) {
-                  p( "+ LED #%d\n", x );
-                }
-              }
-              x = sizeof( buf ); // stop here
-            } else {
-              memset( buf, 0, sizeof( buf ) );
-              x = -1;
-            }
-            break;
-          default:
-            buf[x] = *ch;
-            //p("buf[%d] = %c\n", x, *ch);
-            break;
-          }
-        }
-      } else {
-        p( "LED err: %s", PARAM_ERR );
-        ok = -1;
-      }
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    case 'b':
-    case 'B':
-      i++;
-      if( mode == 0 ) {
-        p("\nBlink\n");
-        mode = MODE_BLINK;
-      } else {
-        p( "%s",MODE_SEL_ERR );
-      }
-      for( x=0; x<sizeof( buf ); x++ ) {
-        i++;
-        ch = ( char * )( macro + i );
-        switch( *ch ) {
-        case ',':
-        case ')':
-          scratch = atoi( buf );
-          //p("got led #%d\n", scratch);
-          if( val1 == -1 ) {
-            p( "got %s %d\n", END_INTS, scratch );
-            val1 = scratch;
-            x = -1;
-          } else {
-            if( freq == -1 ) {
-              p( "got frequency %d\n", scratch );
-              freq = scratch;
-              x = -1;
-            } else {
-              if( repeat == -1 ) {
-                p( "got repeat %d\n", scratch );
-                repeat = scratch;
-                blink_leds( leds, val1, freq, repeat );
-                x = sizeof( buf );
-              } else {
-                p( "Blink set %s", PARAM_ERR );
-              }
-            }
-          }
-          memset( buf, 0, sizeof( buf ) );
-          break;
-        default:
-          buf[x] = *ch;
-          //p("buf[%d] = %c\n", x, *ch);
-          break;
-        }
-      }
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    case 'f':
-    case 'F':
-    case 'p':
-    case 'P':
-      i++;
-      if( mode == 0 ) {
-        if( ( *ch == 'f' ) || ( *ch == 'F' ) ) {
-          mode = MODE_FADE;
-          p( "\nFade\n" );
-        } else {
-          mode = MODE_PULSE;
-          p( "\nPulse\n" );
-        }
-      } else {
-        p( "%s",MODE_SEL_ERR );
-      }
-      for( x=0; x<sizeof( buf ); x++ ) {
-        i++;
-        ch = ( char * )( macro + i );
-        switch( *ch ) {
-        case ',':
-        case ')':
-          scratch = atoi( buf );
-          //p("got led #%d\n", scratch);
-          if( val1 == -1 ) {
-            p( "got %s %d\n",START_INTS, scratch );
-            val1 = scratch;
-            x = -1;
-          } else {
-            if ( val2 == -1 ) {
-              p( "got %s %d\n",END_INTS, scratch );
-              val2 = scratch;
-              x = -1;
-            } else {
-              if( freq == -1 ) {
-                p( "got frequency %d\n", scratch );
-                freq = scratch;
-                x = -1;
-              } else {
-                if( repeat == -1 ) {
-                  p( "got repeat %d\n", scratch );
-                  repeat = scratch;
-                  if( mode == MODE_FADE ) {
-                    fade_leds( leds, val1, val2, freq, repeat );
-                  } else {
-                    pulse_leds( leds, val1, val2, freq, repeat );
-                  }
-                  x = sizeof( buf );
-                } else {
-                  p( "set %s", PARAM_ERR );
-                }
-              }
-            }
-          }
-          memset( buf, 0, sizeof( buf ) );
-          break;
-        default:
-          buf[x] = *ch;
-          //p("buf[%d] = %c\n", x, *ch);
-          break;
-        }
-      }
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    case 'i':
-    case 'I':
-      if( mode == 0 ) {
-        mode = MODE_SET;
-        p( "\nIntensity\n" );
-      } else {
-        p( "%s",MODE_SEL_ERR );
-      }
-      i++;
-      mode = MODE_SET;
-      memset( buf,0, sizeof( buf ) );
-      for( x=0; x<sizeof( buf ); x++ ) {
-        i++;
-        ch = ( char * )( macro + i );
-        switch( *ch ) {
-        case ')':
-          if( freq == -1 ) {
-            scratch = atoi( buf );
-            p( "got %s %d\n", END_INTS, scratch );
-            val1 = scratch;
-            set_leds( leds, val1 );
-            x = sizeof( buf );
-          } else {
-            p( "intensity %s", PARAM_ERR );
-          }
-          break;
-        default:
-          buf[x] = *ch;
-          break;
-        }
-      }
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    case 'w':
-    case 'W':
-      if( ( mode == 0 ) &&  ( *( ch+1 ) == '(' ) ) {
-        i++;
-        p( "\nWait\n" );
-        mode = MODE_WAIT;
-        memset( buf,0, sizeof( buf ) );
-        for( x=0; x<sizeof( buf ); x++ ) {
-          i++;
-          ch = ( char * )( macro + i );
-          switch( *ch ) {
-          case ')':
-            if( freq == -1 ) {
-              scratch = atoi( buf );
-              p( "got freq %d\n", scratch );
-              freq = scratch;
-              delay( freq );
-              x = sizeof( buf );
-            } else {
-              p( "Wait set %s", PARAM_ERR );
-            }
-            break;
-          default:
-            buf[x] = *ch;
-            break;
-          }
-        }
-      } else {
-        p( "%s",MODE_SEL_ERR );
-      }
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    case 'c':
-    case 'C':
-      i++;
-      p( "Clear\n" );
-      set_leds( ALL_LEDS, 0 );
-      //leds = 0;
-      val1 = -1;
-      val2 = -1;
-      freq = -1;
-      wait = - 1;
-      repeat = -1;
-      mode = 0;
-      break;
-    }
-  }// end of loop through macro
-  //p("led = %d\n", leds );
-  return ok;
-}
-
-void unrecognized()
-{
-  p( "\nError!\n" );
-}
-


Animation/fading/transitions with delay time

--- ESP8266HueEmulator/ESP8266HueEmulator.ino
+++ ESP8266HueEmulator/ESP8266HueEmulator.ino
@@ -29,6 +29,7 @@
 RgbColor blue = RgbColor(0, 0, colorSaturation);
 RgbColor white = RgbColor(colorSaturation);
 RgbColor black = RgbColor(0);
+unsigned int transitionTime = 400; // by default there is a transition time to the new state of 400 milliseconds

 /// X, Y, Z and x, y are values to desvribe colors
 float X;
@@ -132,13 +133,13 @@
       Serial.println("parseObject() failed");
       return;
     }
-   bool onValue = root["on"];
+    bool onValue = root["on"];
     Serial.print("I should --> ");
     Serial.println(onValue);
-    if (onValue == true)
-      strip.SetPixelColor(numberOfTheLight - 1, white); // For now we ignore the color (FIXME)
+    if (onValue == true)
+      strip.LinearFadePixelColor(transitionTime, numberOfTheLight - 1, white); // For now we ignore the color (FIXME)
     if (onValue == false)
-      strip.SetPixelColor(numberOfTheLight - 1, black);
+      strip.LinearFadePixelColor(transitionTime, numberOfTheLight - 1, black);
     strip.Show();
   }

@@ -220,8 +221,25 @@
 }

 void loop() {
+
+  // FIXME: This seems to block everything while a request is being processed which takes about 2 seconds
+  // Can we run this in a separate thread, in "the background"?
   HTTP.handleClient();
   SSDP.update();
+
+  // Start animating the NeoPixels
+  strip.StartAnimating();
+
+  // Wait until no more animations are running
+  // FIXME: This seems to block everything while a transition is running
+  // Can we run this in a separate thread, in "the background"?
+  while (strip.IsAnimating())
+  {
+    strip.UpdateAnimations();
+    strip.Show();
+    delay(31); // ~30hz change cycle
+  }
+
   delay(1);
 }

@@ -240,7 +258,7 @@

 void infoLight(RgbColor color) {
   // Flash the strip in the selected color. White = booted, green = WLAN connected, red = WLAN could not connect
-  for (int i = 0; i < 30; i++)
+  for (int i = 0; i < pixelCount; i++)
   {
     strip.SetPixelColor(i, color);
     strip.Show();


v1.1 Improve display of HDOP

v1.1 Improve display of HDOP


Update hello.ino

Update hello.ino

--- hello-world/hello.ino
+++ hello-world/hello.ino
@@ -1,42 +1,30 @@
-//include the framework
-#include "kriFram-0.h"
+
+#include "kriFram.h"

 void setup() {
   // initialize framework.
-  kritagyaSetup();
+  kriFramSetup();

-
-//home page is not declared by framework app should make it
-server.on ( "/home", handleRoot );
-server.on ( "/", handleRoot );
+  Setting("call","Callibrate");
+  server.on ( "/home", handleRoot );
+  server.on ( "/", handleRoot );

-//add custom link on settings page
-addCustomSetting("call","Callibrate");
-//map custom setting page to function
-server.on("/call", handleCall );
-
-
-//start webServer
-server.begin();
-
+  server.begin();
 }

 // the loop function runs over and over again forever
 void loop() {
   //loop framework
-  kritagyaLoop();
+  kriFramLoop();
+
+
+
 }

 void handleRoot() {
-  String temp = "Hello World!";
-  server.send ( 200, "text/html", headder + temp + footer );
+  String body = "Hello World!";
+  server.send ( 200, "text/html", headder + body + footer );
   Serial.println ( "root page sent" );
 }
-
-void handleCall(){
-  String temp = "Hello World!";
-  server.send ( 200, "text/html", headder + temp + footer );
-  Serial.println ( "callibration page sent" );
-}


music glove edit

music glove edit

--- musicglove2/musicglove2.ino
+++ musicglove2/musicglove2.ino
@@ -20,8 +20,8 @@

 /*
   Send register address and the byte value you want to write the magnetometer and
-  loads the destination register with the value you send
-*/
+ loads the destination register with the value you send
+ */
 void Writei2cRegisters(byte numberbytes, byte command)
 {
   byte i = 0;
@@ -37,8 +37,8 @@

 /*
   Send register address to this function and it returns byte value
-  for the magnetometer register's contents
-*/
+ for the magnetometer register's contents
+ */
 byte Readi2cRegisters(int numberbytes, byte command)
 {
   byte i = 0;
@@ -80,7 +80,7 @@

 /*
   Reads the register values for clear, red, green, and blue.
-*/
+ */
 void get_Colors(void)
 {
   unsigned int clear_color = 0;
@@ -108,34 +108,44 @@
   // Basic RGB color differentiation can be accomplished by comparing the values and the largest reading will be
   // the prominent color

-  if ((red_color > blue_color) && (red_color > green_color))
-    Serial.println("detecting red");
-  else if ((green_color > blue_color) && (green_color > red_color))
-    Serial.println("detecting green");
-  else if ((blue_color > red_color) && (blue_color > green_color))
-    Serial.println("detecting blue");
-  else
-    Serial.println("color not detectable");
-
+
   const int sizeRow = 9; // RGB
   const int sizeCol = 3; // nine colors
-  int constanterror = 3500;
+  int constanterror = 5000;
   bool redMatch = false;
   bool greenMatch = false;
   bool blueMatch = false;
   long int ary[sizeRow][sizeCol] =
-  { {19000, 12200, 5500}, // red
-    {12000, 6800, 3750}, // orange
-    {35000, 38700, 15150}, // yellow
-    {6700, 15700, 7800}, // green
-    {6050, 1000, 10200}, // blue
-    {11000, 12500, 10900}, // indigo
-    {5200, 4900, 5100}, // violet
-    {200, 120, 55}, // black
-    {44000, 53100, 34200} // white
+  {
+    {
+      19000, 12200, 5500            }
+    , // red
+    {
+      12000, 6800, 3750            }
+    , // orange
+    {
+      35000, 38700, 15150            }
+    , // yellow
+    {
+      6700, 15700, 7800            }
+    , // green
+    {
+      6050, 1000, 10200            }
+    , // blue
+    {
+      11000, 12500, 10900            }
+    , // indigo
+    {
+      5200, 4900, 5100            }
+    , // violet
+    {
+      200, 120, 55            }
+    , // black
+    {
+      44000, 53100, 34200            } // white
   };
-  String colorary [9] = {"red", "orange", "yellow", "green", "blue", "indigo", "violet", "black", "white"};
-  int switchnum;
+  String colorary [9] = {
+    "red", "orange", "yellow", "green", "blue", "indigo", "violet", "black", "white"      };
   for (int y = 0; y < 9; y++)
   {
     if ((red_color < (ary[0][y] + constanterror)) && (red_color > (ary[0][y] - constanterror)))
@@ -153,46 +163,49 @@
     if ((redMatch == true) && (blueMatch == true) && (greenMatch = true))
     {
       Serial.println(colorary[y]);
-      switchnum = y;
+      switch(y)
+      {
+      case 0:
+        playNote("C", 4, 300);
+        break;
+      case 1:
+        playNote("D", 4, 300);
+        break;
+      case 2:
+        playNote("E", 4, 300);
+        break;
+      case 3:
+        playNote("F", 4, 300);
+        break;
+      case 4:
+        playNote("G", 4, 300);
+        break;
+      case 5:
+        playNote("A", 4, 300);
+        break;
+      case 6:
+        playNote("B", 4, 300);
+        break;
+      }
       break;
     }
-    switch(switchnum)
-    {
-      case 0:
-      playNote("C", 4, 300);
-      break;
-      case 1:
-      playNote("D", 4, 300);
-      break;
-      case 2:
-      playNote("E", 4, 300);
-      break;
-      case 3:
-      playNote("F", 4, 300);
-      break;
-      case 4:
-      playNote("G", 4, 300);
-      break;
-      case 5:
-      playNote("A", 4, 300);
-      break;
-      case 6:
-      playNote("B", 4, 300);
-      break;
-    }
-  }
-}
-
-String notes[] = {"C","C#","D","D#","E","F","F#","G","G#","A","A#","B"};
+
+  }
+}
+
+String notes[] = {
+  "C","C#","D","D#","E","F","F#","G","G#","A","A#","B"};
 int index;

 void noteOn(byte channel, byte pitch, byte velocity) {
-  MIDIEvent noteOn = {0x09, 0x90 | channel, pitch, velocity};
+  MIDIEvent noteOn = {
+    0x09, 0x90 | channel, pitch, velocity      };
   MIDIUSB.write(noteOn);
 }

 void noteOff(byte channel, byte pitch, byte velocity) {
-  MIDIEvent noteOff = {0x08, 0x80 | channel, pitch, velocity};
+  MIDIEvent noteOff = {
+    0x08, 0x80 | channel, pitch, velocity      };
   MIDIUSB.write(noteOff);
 }

@@ -205,7 +218,7 @@
   noteOn(0, index+octave*12, 64);
   MIDIUSB.flush();
   delay(t);
-
+
   noteOff(0, index+octave*12, 64);
   MIDIUSB.flush();
 }
@@ -239,9 +252,11 @@
   }
   else if (state == '1') {
     digitalWrite(ledPin, HIGH);
-    Serial.println("LED: ON");;
-    state = 0;
-  } if (Serial.available() > 0) { // Checks whether data is comming from the serial port
+    Serial.println("LED: ON");
+    ;
+    state = 0;
+  }
+  if (Serial.available() > 0) { // Checks whether data is comming from the serial port
     state = Serial.read(); // Reads the data from the serial port
   }
   if (state == '0') {
@@ -251,7 +266,14 @@
   }
   else if (state == '1') {
     digitalWrite(ledPin, HIGH);
-    Serial.println("LED: ON");;
-    state = 0;
-  }
-}
+    Serial.println("LED: ON");
+    ;
+    state = 0;
+  }
+  Wire.beginTransmission(8);
+  Wire.endTransmission();
+  //
+}
+
+
+


Fix text shown on serial monitor.

Fix text shown on serial monitor.

--- examples/Voltage16Ch/Voltage16Ch.ino
+++ examples/Voltage16Ch/Voltage16Ch.ino
@@ -14,7 +14,7 @@
 void setup()
 {
   Serial.begin(9600);
-  Serial.println("ADC Nanoshield Test - Voltage Measurement - 16 x 12-bit");
+  Serial.println("ADC Nanoshield Test - Voltage Measurement - 16 x 16-bit");
   Serial.println("");

   for (int i = 0; i < 4; i++) {


Update hdc1010demo.ino

Update hdc1010demo.ino

--- examples/hdc1010demo/hdc1010demo.ino
+++ examples/hdc1010demo/hdc1010demo.ino
@@ -19,6 +19,8 @@
 #include "ClosedCube_HDC1010.h"
 #include <Wire.h>

+#include HDC1010_I2C_ADDRESS 0x48
+
 ClosedCube_HDC1010 hdc1010;

 void setup()
@@ -26,7 +28,7 @@
 	Serial.begin(9600);
 	Serial.println("ClosedCube HDC1010 Arduino Test");

-	hdc1010.begin(0x41);
+	hdc1010.begin(HDC1010_I2C_ADDRESS);

 	Serial.print("Manufacturer ID=0x");
 	Serial.println(hdc1010.readManufacturerId(), HEX); // 0x5449 ID of Texas Instruments


clean project

clean project

--- arduino/arduibiew-lm35/arduibiew-lm35.ino
+++ arduino/arduibiew-lm35/arduibiew-lm35.ino
@@ -1,256 +0,0 @@
-#include <Adafruit_CC3000.h>
-#include <Adafruit_CC3000_Server.h>
-#include <ccspi.h>
-
-/***************************************************
- * This is an example for the DFRobot Wido - Wifi Integrated IoT lite sensor and control node
- * Product Page & More info: http://www.dfrobot.com.cn/goods-997.html
- * Designed specifically to work with the DFRobot Wido products:
- *
- * The library is forked from Adafruit
- *
- * Written by Lauren
- * BSD license, all text above must be included in any redistribution
- *
- ****************************************************/
-
-/*
-This example code is used to connect the Yeelink cloud service (Official homepage: www.yeelink.net).
-
- The device required is just:
-
- 1. LM35 low cost temperature sensor or any device you used to upload data
- 2. And Wido
-
-Note: Please don't forget to change the setting below before using!
- 1. WLAN_SSID & WlAN_PASS
- 2. API_key
- 3. device ID & sensor ID
-
- */
-
-
-#include <Adafruit_CC3000.h>
-#include <ccspi.h>
-#include <SPI.h>
-#define Wido_IRQ   3
-#define Wido_VBAT  5
-#define Wido_CS    10
-
-Adafruit_CC3000 Wido = Adafruit_CC3000(Wido_CS, Wido_IRQ, Wido_VBAT,
-                                       SPI_CLOCK_DIVIDER); // you can change this clock speed
-
-// Security can be WLAN_SEC_UNSEC, WLAN_SEC_WEP, WLAN_SEC_WPA or WLAN_SEC_WPA2
-#define WLAN_SECURITY   WLAN_SEC_WPA2
-
-
-#define WLAN_SSID       "xiaomi"           // cannot be longer than 32 characters!
-#define WLAN_PASS       "18600503761"          // For connecting router or AP, don't forget to set the SSID and password here!!
-
-#define DEVICE_ID       "561083be06dd6162658ae8c8"  //arduiview device id
-
-
-#define TCP_TIMEOUT      3000
-//#define CC3000_TINY_DRIVER
-
-#define WEBSITE  "arduiview.herokuapp.com"
-
-
-uint32_t ip = 0;
-float temp = 0;
-
-
-static Adafruit_CC3000_Client WidoClient;
-static unsigned long RetryMillis = 0;
-static unsigned long uploadtStamp = 0;
-static unsigned long sensortStamp = 0;
-
-
-void setup() {
-
-  Serial.begin(115200);
-
-  initWifiConnection();
-
-}
-
-
-void loop() {
-
-
-
-
-  // ======= build the connectioin =========
-  if (!WidoClient.connected() && millis() - RetryMillis > TCP_TIMEOUT) {
-    // Update the time stamp
-    RetryMillis = millis();
-
-    Serial.println(F("Try to connect the cloud server"));
-    WidoClient.close();
-
-    // Get cloud server IP address
-    Serial.print(WEBSITE);
-    while  (ip  ==  0)  {
-      if  (!Wido.getHostByName(WEBSITE, &ip))  {    //  Get the server IP address based on the domain name
-        Serial.println(F("Couldn't resolve!"));
-      }
-      Serial.println(F("resolved IP failed, retrying...."));
-      delay(500);
-
-    }
-    Wido.printIPdotsRev(ip);
-    Serial.println(F(" IP resolved."));
-
-    // Connect to the aruduiview Server
-    WidoClient = Wido.connectTCP(ip, 80);          // Try to connect cloud server
-
-    Serial.println(F("connected."));
-  }
-
-
-  //===========Upload data ========
-  if (WidoClient.connected() && millis() - uploadtStamp > 2000) {   //upload every 2s
-    uploadtStamp = millis();
-    // If the device is connected to the cloud server, upload the data every 2000ms.
-
-    Serial.println(F("Begin uploading...."));
-
-    // Prepare Http Package for Yeelink & get length
-    int length = 0;
-    char lengthstr[3];
-
-    // Create Http data package
-    char httpPackage[] = "";
-
-    strcat(httpPackage , "{\"value\": \"");
-
-    //get temperature from sensor
-    int reading = analogRead(0);
-    temp = reading * 0.0048828125 * 100;
-    Serial.print(F("Real Time Temp: "));
-    Serial.println(temp);
-
-    char sTemp[] = "";
-    //convert float to char*,
-     //dtostrf(temp,2,2, sTemp); //val, integer part width, precise, result char array
-    itoa(temp, sTemp, 10);
-    strcat(httpPackage , sTemp);    // push the data(temp) to the http data package
-    strcat(httpPackage , "\" }");
-
-    length = strlen(httpPackage);                           // get the length of data package
-    itoa(length, lengthstr, 10);                            // convert int to char array for posting
-    //Serial.print(F("Length = "));
-    //Serial.println(length);
-
-    // Send headers
-    Serial.print(F("Sending headers"));
-
-    WidoClient.fastrprint(F("PUT /api/sensors/"));
-    char *deviceId = DEVICE_ID;
-    WidoClient.fastrprint(deviceId);
-    WidoClient.fastrprint(F("/values"));
-
-    WidoClient.fastrprintln(F(" HTTP/1.1"));
-    Serial.print(F("."));
-
-    WidoClient.fastrprintln(F("Host: arduiview.herokuapp.com"));
-    Serial.print(F("."));
-
-    WidoClient.fastrprint(F("content-type: "));
-    WidoClient.fastrprintln("application/json");
-    Serial.print(F("."));
-
-    WidoClient.fastrprint("Content-Length: ");
-    WidoClient.fastrprintln(lengthstr);
-    WidoClient.fastrprintln("");
-    Serial.print(F("."));
-
-    Serial.println(F(" done."));
-
-    // Send data
-    Serial.print(F("Sending data"));
-
-    //char payload[600] = "";
-    //strcat(payload,httpPackage);
-    WidoClient.fastrprintln(httpPackage);
-
-    //Serial.println(F("-----"));
-    //Serial.println(httpPackage);
-    //Serial.println(F("-----"));
-
-    Serial.println(F(" done."));
-
-    /********** Get the http page feedback ***********/
-
-    unsigned long rTimer = millis();
-    Serial.println(F("Reading Cloud Response!!!\r\n"));
-    while (millis() - rTimer < 2000) {
-      while (WidoClient.connected() && WidoClient.available()) {
-        char c = WidoClient.read();
-        Serial.print(c);
-      }
-    }
-    delay(1000);             // Wait for 1s to finish posting the data stream
-    WidoClient.close();      // Close the service connection
-
-   }
-
-
-  //  //read temperature every 0.1 seconds
-  //  if (millis() - sensortStamp > 100) {
-  //    sensortStamp = millis();
-  //    // read the LM35 sensor value and convert to the degrees every 100ms.
-  //
-  //    int reading = analogRead(0);
-  //    temp = reading * 0.0048828125 * 100;
-  //    Serial.print(F("Real Time Temp: "));
-  //    Serial.println(temp);
-  //  }
-}
-
-
-
-void initWifiConnection() {
-
-  /* Initialise the module */
-  Serial.println(F("\nInitialising the CC3000 ..."));
-  if (!Wido.begin())
-  {
-    Serial.println(F("Unable to initialise the CC3000! Check your wiring?"));
-    while (1);
-  }
-
-  /* Attempt to connect to an access point */
-  char *ssid = WLAN_SSID;             /* Max 32 chars */
-  Serial.print(F("\nAttempting to connect to "));
-  Serial.println(ssid);
-
-  /* NOTE: Secure connections are not available in 'Tiny' mode!
-   By default connectToAP will retry indefinitely, however you can pass an
-   optional maximum number of retries (greater than zero) as the fourth parameter.
-   */
-  if (!Wido.connectToAP(WLAN_SSID, WLAN_PASS, WLAN_SECURITY)) {
-    Serial.println(F("Failed!"));
-    while (1);
-  }
-
-  Serial.println(F("Connected to WIFI!"));
-
-  /* Wait for DHCP to complete */
-  Serial.println(F("Request DHCP"));
-  while (!Wido.checkDHCP())
-  {
-    delay(1000); // ToDo: Insert a DHCP timeout!
-  }
-
-
-}
-
-
-
-
-
-
-
-
-


CMD list in version string corrected; matches parseCommand().

`parseCommand()` defines commands as:

```
R: READ_HEX
r: READ_BIN
W: WRITE_HEX
w: WRITE_BIN
V: VERSION
```

This patch fixes the command list advertised in the version string to match that list; `R,r,w,W,V`

--- Arduino/MEEPROMMERfirmware/MEEPROMMERfirmware.ino
+++ Arduino/MEEPROMMERfirmware/MEEPROMMERfirmware.ino
@@ -14,7 +14,7 @@
  *
  **/

-#define VERSIONSTRING "MEEPROMMER $Revision: 1.2 $ $Date: 2013/05/05 11:01:54 $, CMD:B,b,w,W,V"
+#define VERSIONSTRING "MEEPROMMER $Revision: 1.2 $ $Date: 2013/05/05 11:01:54 $, CMD:R,r,w,W,V"

 // shiftOut part
 #define DS      A0


Code/Sketch updated add "Scope" mode to the 16x2 Display.
This change gives the user the option to view the Spindle speed pulses
using the Arduino's A1 pin, much the same way you would using a traditional
oscilloscope, but with the limitations of a 80x32 matrix affords the viewer

Signed-off-by: jmhrvy <6a3cd8a1b2d47d05877db3d1fefa06cbe0a9a3f0@epbfi.com>

--- CNCSpindleSpeedControl/CNCSpindleSpeedControl.ino
+++ CNCSpindleSpeedControl/CNCSpindleSpeedControl.ino
@@ -1,5 +1,5 @@
 /*
-This Program when loaded on an Arduino/Leonardo is a Tach based speed controller.
+This Program when uploaded to a Arduino/Leonardo (or Uno) is a Tach based speed controller.
 It was originally written to operate a 400W/48VDC CNC spindle motor through
 a simple electronic controller, readily found on E-Bay
 This program assumes that the +PWM lead of the controller is connected to
@@ -13,10 +13,35 @@
 can be used to ramp the Set Speed from 1400 to 10,000 RPM, in steps of 200 RPM,
 while the Left/Right Buttons will select the display mode.

+This version of the speed control sketch incudes a "Scope" display mode. This mode
+is new to this release. To access the Scope mode, press either the "Left" or "Right"
+buttons on the display's key pad. Hint: using the "Left" button, it will be the first key press.
+The purpose of this mode is to allow the user, to use the 16 x 2 display as a rudimentary
+Oscilloscope. The Arduino's "A1" pin acts as the Scope's input. Typically either the IR's Output signal
+which is normally connected to the Arduino's interrupt pin (D3) can be also connected to A1.
+This gives the user a practical way to observe the spindle's speed signal. And through this view,
+the user can adjust the IR sensor's position for maximum effectiveness.
+The ideal pulse should look something like what is shown here:
+ /--------------------\   /-----
+/                      \-/
+It may be helpful to make the initial position adjustments with the IR's output only connected to
+A1 (interrupt pin D3 not connected). With this arrangement the spindle should run at a steady
+speed regardless of what the sensor is outputing, and will allow the user to explore a range of positions
+without the spindle speed going crazy. Once the best spot it found, add the interrupt connection, and
+then the user can "fine tune" this position by continuing to monitor the speed pulse on A1.
+
 Note: The LCDKeypadR1 Library, contained in this file set,
 is a derivative of the files found here:

 http://sainsmart.com/zen/documents/20-011-901/keypad_lcd.zip
+
+To install this sketch, when down loaded from GitHub all the files found under the sub-directory
+"CNCSpindleSpeedControl" should be left in that directory. and the entire directory
+[CNCSpindleSpeedControl] moved to the same directory as the Uer's other sketches
+On a windows based computer, this is usually the /Documents/Arduino/ directory.
+If setup correctly, when you open the sketch, you should see three tabs.
+"CNCSpindleSpeedControl", "LCDKeypadR1.cpp", and "LCDKeypadR1.h"
+

 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
@@ -76,11 +101,8 @@

 int PWMpin; // Digital Pin that PWM signal appears on (Pin 13 = Leonardo; Pin 11 = Uno)
 int calcrpm = 0;
-int GPIOpin = 1; // Use pin "0" [Pi IO header pin 11] to simulate a Clk pulse s$
-//int GPIOpinSlow = 4; //Under Speed LED
-//int GPIOpinOK = 5; //Speed Ok LED
-//int GPIOpinFast = 6; //Over Speed LED
-
+int sensorPin = A1; // Used for Oscope Mode (mode 3)
+int IRAnalogBuf[80];// Buffer/Array to hold Scaled analog data Used for Oscope Mode (mode 3)
 // -----------------PID/PWM Constants -----------------
 unsigned long lastTime;
 double Input, SetPoint;
@@ -196,6 +218,35 @@
   0b11111,
   0b11111
 } ;
+
+
+// O-Scope bitmap
+static unsigned char Char0101 [16];
+static unsigned char Char0102 [16];
+static unsigned char Char0103 [16];
+static unsigned char Char0104 [16];
+static unsigned char Char0105 [16];
+static unsigned char Char0106 [16];
+static unsigned char Char0107 [16];
+static unsigned char Char0108 [16];
+static unsigned char Char0109 [16];
+static unsigned char Char0110 [16];
+static unsigned char Char0111 [16];
+static unsigned char Char0112 [16];
+static unsigned char Char0113 [16];
+static unsigned char Char0114 [16];
+static unsigned char Char0115 [16];
+static unsigned char Char0116 [16];
+static unsigned char Trace1 [8];
+static unsigned char Trace2 [8];
+static unsigned char Trace3 [8];
+static unsigned char Trace4 [8];
+static unsigned char Trace5 [8];
+static unsigned char Trace6 [8];
+static unsigned char Trace7 [8];
+static unsigned char Trace8 [8];
+static unsigned char TstBtMap [8];
+

 // ================================================================
 // ===               INTERRUPT DETECTION ROUTINE                ===
@@ -255,7 +306,7 @@
 {
   byte Divisor;
   //Serial1.begin(9600); // enable when [Leonardo] bluetooth diagnostic is needed
-  //Serial.begin(9600);  // enable when/if diagnostic is needed
+  Serial.begin(9600);  // enable when/if diagnostic is needed
    // set up the lcd's number of columns and rows:
   lcd.begin(16, 2);
   //calcrpm =  (SampleCnt*1000000*60)/period;//Formula used in interrupt routine to estimate current Spindle RMPM
@@ -279,18 +330,7 @@

   TimerReg = TimerReg & 0b11111000 | Divisor;
   pinMode(PWMpin, OUTPUT);
-// install  user defined special characters
-  lcd.createChar(0, Char0);
-  // create a new character
-  lcd.createChar(1, Char1);
-  // create a new character
-  lcd.createChar(2, Char2);
-  // create a new character
-  lcd.createChar(3, Char3);
-  // create a new character
-  lcd.createChar(4,Char4);
-  // create a new character
-  lcd.createChar(5, Char5);
+
   //lcd.setCursor(0,0);
   //lcd.print("SetUp Complete");
   //startPrgm = 1000*millis();
@@ -332,11 +372,12 @@
      {
       //Motor is not running, So initialize PID for next startup
       //SpndlPWM = (int) 190.5*(trgtRPM/9800.0)*(trgtRPM/9800.0) ;
+      ResetSpindle();
       SpndlPWM = 15;
-      SetPoint = 2000;
-      ITerm = 0.0; //kill any residual Integral component that might be left over from a previous run
-      lastTime = millis();// reset/establish time mark for initial PID calculation
-      analogWrite(PWMpin, SpndlPWM); //start the PWM output
+//      SetPoint = 2000;
+//      ITerm = 0.0; //kill any residual Integral component that might be left over from a previous run
+//      lastTime = millis();// reset/establish time mark for initial PID calculation
+//      analogWrite(PWMpin, SpndlPWM); //start the PWM output
       //sprintf (buf, "PWMpin:%02i PWM:%02i", PWMpin, SpndlPWM);
       //Serial.println(buf);
       //Startup, in this version of the code is not used
@@ -353,6 +394,12 @@
        }
       UsrInput =  ScanButtons();
       UpDateSettings(UsrInput, Mode);
+      while (Mode == 3){// Run Scope Mode Routine
+      ScopeMode();
+      UsrInput =  ScanButtons();
+      UpDateSettings(UsrInput, Mode);
+      }
+
       long TotalRunTime = calcruntime();
       //SuspectRdCnt = 3;
       stopCnt = stopCnt+1;
@@ -470,12 +517,11 @@
       }
     }
 // ############ End BarGraph Mode #################
-   if (Mode == 3)// Set Back Light Color Mode
-    {
-      //lcdPrintf (lcdHandle,"Set Display Clr ");
-      //sprintf (buf, "%s%s ", "Spd Err:", calcrpm);
-     lcd.print("Set Display Clr ");
-    }
+   if (Mode == 3){// Run Scope Mode Routine
+    ScopeMode();
+   }
+// ############ End O-Scope Mode #################
+
    UsrInput =  ScanButtons();
    UpDateSettings(UsrInput, Mode);
    delay( 250 ); // wait 1/4 second(s)
@@ -495,15 +541,6 @@
  //kill the PWM signal
   detachInterrupt(InterruptId);
   digitalWrite (PWMpin, LOW);
-// pinMode (GPIOpin, OUTPUT) ; //configure pin 1 as a simple output pin
-// digitalWrite (GPIOpin, LOW); //set/force pin 1 output to ground [low]
-// digitalWrite (GPIOpinSlow, LOW); //set/force pin 4 output High[Under Speed LED off]
-// digitalWrite (GPIOpinOK, LOW); //set/force pin 5 output  High[Speed Ok LED off]
-// digitalWrite (GPIOpinFast, LOW); //set/force pin 6 output  High[Over Speed LED off]
-
-
- //Serial1.print("All Done!\n");
- //setBacklightColour (0);
  lcd.clear();
  lcd.setCursor(0,0); //lcd.setCursor(pos,line)
  sprintf (buf, "Program Stopped");
@@ -675,26 +712,35 @@
       if((UsrInput == 4 || UsrInput == 8) && NuInput == true) //[Display Left o$
        {
 //        Serial1.print("NuInput %s\n", NuInput ? "true" : "false");
+        if (Mode == 3){ //user is leaving Scope mode so restore Display
+          lcd.setCursor(0,0);
+          lcd.clear();
+          sprintf (buf,"Trgt RPM: %d", trgtRPM);
+          lcd.print(buf);
+        }
+
+
         NuInput = false;
         if (UsrInput == 4)
          {
            Mode = Mode +1;
            if (Mode == 8)
             {
-              //Mode = 3;
-              Mode = 4;
+              Mode = 3;
+              //Mode = 4;
             }
          }
         else
          {
            Mode = Mode- 1;
-           if (Mode == 3)//if (Mode == 2)
+           if (Mode == 2)
             {
               Mode = 7;
             }

          }
         //setBacklightColour (BackLight);
+        if (Mode == 4) LoadBarGraphFont();//user just selected bargraph mode; load custom characters to support
        }
       if (UsrInput ==16)
        {
@@ -715,17 +761,366 @@
   return RunTime;
 }
 // -------------------------------------------------------------------------
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+void ResetSpindle(){
+  SpndlPWM = 15;
+  SetPoint = 2000;
+  ITerm = 0.0; //kill any residual Integral component that might be left over from a previous run
+  lastTime = millis();// reset/establish time mark for initial PID calculation
+  analogWrite(PWMpin, SpndlPWM); //start the PWM output
+}
+// -------------------------------------------------------------------------
+
+void LoadBarGraphFont(){
+  // install  user defined special characters
+  lcd.createChar(0, Char0);
+  // create a new character
+  lcd.createChar(1, Char1);
+  // create a new character
+  lcd.createChar(2, Char2);
+  // create a new character
+  lcd.createChar(3, Char3);
+  // create a new character
+  lcd.createChar(4,Char4);
+  // create a new character
+  lcd.createChar(5, Char5);
+}
+// -------------------------------------------------------------------------
+void ScopeMode(){
+  int AsmplCnt =0 ;
+  int sensorValue;
+  int RowWeight = 64;
+  bool KeepWaiting = true;
+  unsigned long LoopTime;
+  unsigned long GoNow = micros();
+  AsmplCnt =0;
+  int uSWait = (int)((period/(SampleCnt*10))-900)/8; // returns the number of micro seconds to wait/sample to collect 80 data points given the current spindle speed
+//      Serial.println("Mode3");
+  while(eventCounter == 0 & KeepWaiting){
+    LoopTime = micros()-GoNow;
+    if (LoopTime > 300000){
+      KeepWaiting = false;
+    }
+  }
+  while (eventCounter != 0 & KeepWaiting){
+
+    LoopTime = micros()-GoNow;
+    if (LoopTime > 300000){
+      KeepWaiting = false;
+    }
+  }
+  if(KeepWaiting){ // if true, we are receiving interrupts; So use the interrupt method to establish sample frequency
+    GoNow = micros();
+    unsigned long pause = (period/(SampleCnt))/2;
+    while (KeepWaiting){
+      LoopTime = micros()-GoNow;
+      if (LoopTime > pause){
+        KeepWaiting = false;
+      }
+    }
+    //Serial.println("Interrupt Trigger");
+    while (AsmplCnt<80){ //while (eventCounter < 2 & AsmplCnt<80){
+       sensorValue = 1024-analogRead(sensorPin);
+       int Drow = 0;
+       int RowVal=0;
+       while (RowVal< sensorValue){
+         RowVal = RowVal+RowWeight;
+         Drow++;
+       }
+       IRAnalogBuf[AsmplCnt] = Drow;
+       AsmplCnt++;
+       GoNow = micros()+uSWait;//150;//
+       while (micros()< GoNow);
+
+    }
+  }
+  else{ // no interrupts detected, try to look for a dip in the analog sense reading to sync/start sample timing
+    //Serial.println("Slope Trigger");
+    ResetSpindle();
+    GoNow = micros();
+    uSWait = 90;
+    LoopTime = 000;
+    while(analogRead(sensorPin)< 800 & LoopTime<60000){ // wait long enough for a motor turning at at least 1,000 rpm to generate a dip in the analog reading
+      LoopTime = micros()-GoNow;
+    }
+    while(analogRead(sensorPin)> 600 & LoopTime<60000){ // wait long enough for a motor turning at at least 1,000 rpm to generate a dip in the analog reading
+      LoopTime = micros()-GoNow;
+    }
+    while (AsmplCnt<80){
+       sensorValue = 1024-analogRead(sensorPin);
+       int Drow = 0;
+       int RowVal=0;
+       while (RowVal< sensorValue){
+         RowVal = RowVal+RowWeight;
+         Drow++;
+       }
+       IRAnalogBuf[AsmplCnt] = Drow;
+       AsmplCnt++;
+       GoNow = micros()+uSWait;//150;//
+       while (micros()< GoNow);
+
+    }
+
+  }
+//      sprintf (buf, "uSwait:%d   ",  uSWait);
+//      Serial.println(buf);
+  IRAnalogBuf[AsmplCnt] =-1;
+  MapBuf2BitMap();
+  LoadTrace();
+//      for( int i=0; i< 16; i++){
+//      sprintf (buf, "%d,",Char0101[i]);
+//      Serial.println(buf);
+//      }
+
+
+//      for( int i=0; i< 80; i++){
+//       sprintf (buf, "%d, ",IRAnalogBuf[i]);
+//       Serial.print(buf);
+//       //Serial.print(", ");
+//      }
+//      Serial.println("");
+  //sprintf (buf, "%s%d   ", "Period:", uSWait);
+//      sprintf (buf, "%s%d ", "Smpl Cnt:", AsmplCnt);
+//      lcd.print(buf);
+
+
+}// End Scope Mode Function
+// -------------------------------------------------------------------------
+
+void MapBuf2BitMap(){// takes the 80 analog samples just collected & creates 16 5x16 bitmaps [16 x 5= 80]
+  int ChrPos = 1;
+  unsigned char *BktPtr;
+  unsigned char BitMask = 0b10000;
+  ResetArrays();// clears out old data such that each of the 16 buckets have 5 bit zereos in each of their 16 rows
+  BktPtr =Rtn5x16BktPtr(ChrPos);
+  for (int i = 0; IRAnalogBuf[i] != -1; i++){
+//         sprintf(buf,"%d, %d\n\r",IRAnalogBuf[i]-1,BitMask);
+//         Serial.print(buf);
+         *(BktPtr+(IRAnalogBuf[i]-1))= *(BktPtr+(IRAnalogBuf[i]-1)) | BitMask;
+         //*(BktPtr+2)= *(BktPtr+2) | BitMask; // For testing synsthesize a straight trace
+          BitMask = (unsigned int)BitMask>>1;
+          if (BitMask == 0){
+            BitMask = 0b10000;
+            ChrPos++;
+            BktPtr =Rtn5x16BktPtr(ChrPos);
+//            Serial.print(i);
+//            Serial.print(", ");
+          }
+    }// end "for" loop
+}
+
+
+
+
+void ResetArrays(){
+  unsigned char *BktPtr;
+  for(int DatAry = 1; DatAry < 17; DatAry++){
+    BktPtr =Rtn5x16BktPtr(DatAry);
+    for (int i = 0 ; i < 16; i++){
+      *(BktPtr+i) = 0b00000;
+    }
+  }
+}
+
+
+void ResetCstmChars(){
+  unsigned char *BktPtr;
+  for(int DataAry = 1; DataAry < 9; DataAry++){
+    BktPtr =RtnSpclChrPtr(DataAry);
+    for (int i = 0 ; i < 8; i++){
+      *(BktPtr+i) = 0b11111;
+    }
+  }
+}
+
+void LoadTrace(){// Draw Oscilloscope Trace (Using Scaled Analog just collected) on 16x2 SanSmart Display
+  int SpclChrCnt = 0;
+  int Line1 [16]; // bucket to hold 1st line of 16 bitmaps to be displayed
+  int Line2 [16]; // bucket to hold 2nd line of 16 bitmaps to be displayed
+  unsigned char *TracePtr;  // create another Pointer label
+  unsigned char *TstPtr;// create another Pointer label
+  ResetCstmChars();
+  // now sequence through the 5x16 bitmaps, & from the custom bitmap collection, assigm them as needed to each of the 16 Display grids/positions in line1 & line2
+  unsigned char *BktPtr;
+  for (int ColPos = 1 ; ColPos < 17; ColPos++){
+    BktPtr =Rtn5x16BktPtr(ColPos);
+     // Now for the current character position, extract a 5x8 bitmap for the 1st line of the display
+     // Then determine if it matches one of the exixting custom characters; If not, add it to the custom character collection (max of 8)
+     for (int i = 0 ; i < 8; i++){
+      TstBtMap[i]= *(BktPtr+i);
+     }
+     // next check the existing special character bitmaps to see if this TstBtMap has a match
+     TstPtr = &TstBtMap[0];
+     int MatchingChr = TstBtMp4Match(SpclChrCnt, TstPtr);
+     if (MatchingChr != -1){ Line1[ColPos-1] = MatchingChr;
+//     Serial.println("Yes");
+     }
+     else {// no match; it's a new bitmap
+       SpclChrCnt++;
+//       sprintf (buf, "NO %d",SpclChrCnt);
+//      Serial.println(buf);
+       if(SpclChrCnt<9){// we haven't yet maxed out the number of custom characters we can define; So add this one to the collection
+         TracePtr = RtnSpclChrPtr(SpclChrCnt);// get a pointer to the next available custom bitmap bucket
+         for (int i = 0 ; i < 8; i++){// transfer the contents of this 5x8 bitmap to our newly select custom bitmap bucket
+            *(TracePtr+i)= *(TstPtr+i);
+          }
+         Line1[ColPos-1] = SpclChrCnt-1; //update the line 1 bucket so that it can later tell the display where to find this custom bitmap
+       }
+       else {Line1[ColPos-1] = -1;
+ //      Serial.println("OverFlow");
+       }
+     }
+     // Now for the current character position, repeat the above process but use the lower 1/2 of the 5x16 bitmapbucket for the 2nd line of the display
+     for (int i = 0 ; i < 8; i++){
+      TstBtMap[i]= *(BktPtr+(i+8));
+     }
+     // now check the existing special character bitmaps to see if this TstBtMap for a match
+     TstPtr = &TstBtMap[0];
+     MatchingChr = TstBtMp4Match(SpclChrCnt, TstPtr);
+     if (MatchingChr != -1) Line2[ColPos-1] = MatchingChr;
+     else {
+       SpclChrCnt++;
+       if(SpclChrCnt<9){
+         TracePtr = RtnSpclChrPtr(SpclChrCnt);
+         for (int i = 0 ; i < 8; i++){
+            *(TracePtr+i)= *(TstPtr+i);
+          }
+         Line2[ColPos-1] = SpclChrCnt-1;
+       }
+       else Line2[ColPos-1] = -1;
+     }
+  } //End for Loop
+  // now load this round's custom charater Set into the 16x2's user defined character ram/registers (max limit of 8)
+  for (int i = 0 ; i < SpclChrCnt & i < 8; i++){
+    TracePtr = RtnSpclChrPtr(i+1);
+    lcd.createChar(i, TracePtr);
+  }
+  // now write out the character assignments to the first line
+  lcd.setCursor(0,0); //lcd.setCursor(pos,line)
+  for (int i = 0 ; i < 16; i++){
+    if(Line1[i]!= -1) lcd.write(byte(Line1[i]));
+    else lcd.print(" ");//lcd.write(byte(3));
+//    sprintf (buf, "%d, ",Line1[i]);
+//    Serial.print(buf);
+  }
+//  Serial.println("");
+  // now write out the character assignments to the 2nd line
+  lcd.setCursor(0,1); //lcd.setCursor(pos,line)
+  for (int i = 0 ; i < 16; i++){
+    if(Line2[i]!= -1 ) lcd.write(byte(Line2[i]));
+    else lcd.print(" ");//lcd.write(byte(3));
+//    sprintf (buf, "%d, ",Line2[i]);
+//    Serial.print(buf);
+  }
+//  Serial.println("");
+}//end of LoadTrace() function
+
+
+
+int TstBtMp4Match(int SpclChrCnt, unsigned char *TstPtr){
+  unsigned char *TracePtr;
+  bool IsSame = true;
+  int RtnPtr = -1;
+  if (SpclChrCnt == 0) return RtnPtr;
+  for (int CurSpclBtMp = 1; CurSpclBtMp < SpclChrCnt+1 & CurSpclBtMp < 9 ; CurSpclBtMp++){
+    IsSame = true;
+    TracePtr = RtnSpclChrPtr(CurSpclBtMp);
+    for (int i = 0 ; i < 8; i++){
+        if(*(TstPtr+i)!= *(TracePtr+i)) IsSame = false;
+      }
+    if (IsSame) return CurSpclBtMp-1;
+  }
+  return RtnPtr;
+}
+
+
+unsigned char* RtnSpclChrPtr(int SpclChrCnt){ // returns a pointer to the designated bitmap array
+  unsigned char *TracePtr;
+  switch (SpclChrCnt) {
+   case 1:
+    TracePtr = &Trace1[0];// assosciate the pointer to the Sat1 array
+     break;
+   case 2:
+     TracePtr = &Trace2[0];// assosciate the pointer to the Sat2 array
+     break;
+   case 3:
+     TracePtr = &Trace3[0];// assosciate the pointer to the Sat3 array
+     break;
+   case 4:
+     TracePtr = &Trace4[0];// assosciate the pointer to the Sat4 array
+     break;
+   case 5:
+    TracePtr = &Trace5[0];// assosciate the pointer to the Sat1 array
+     break;
+   case 6:
+     TracePtr = &Trace6[0];// assosciate the pointer to the Sat2 array
+     break;
+   case 7:
+     TracePtr = &Trace7[0];// assosciate the pointer to the Sat3 array
+     break;
+   case 8:
+     TracePtr = &Trace8[0];// assosciate the pointer to the Sat4 array
+     break;
+ }
+ return TracePtr;
+}
+
+
+
+unsigned char* Rtn5x16BktPtr(int ChrPos){ // returns a pointer to the designated bitmap array
+  unsigned char *BktPtr;
+ switch (ChrPos) {
+       case 1:
+        BktPtr = &Char0101[0];// assosciate the pointer to the Sat1 array
+         break;
+       case 2:
+         BktPtr = &Char0102[0];// assosciate the pointer to the Sat2 array
+         break;
+       case 3:
+         BktPtr = &Char0103[0];// assosciate the pointer to the Sat3 array
+         break;
+       case 4:
+         BktPtr = &Char0104[0];// assosciate the pointer to the Sat4 array
+         break;
+       case 5:
+        BktPtr = &Char0105[0];// assosciate the pointer to the Sat1 array
+         break;
+       case 6:
+         BktPtr = &Char0106[0];// assosciate the pointer to the Sat2 array
+         break;
+       case 7:
+         BktPtr = &Char0107[0];// assosciate the pointer to the Sat3 array
+         break;
+       case 8:
+         BktPtr = &Char0108[0];// assosciate the pointer to the Sat4 array
+         break;
+       case 9:
+        BktPtr = &Char0109[0];// assosciate the pointer to the Sat1 array
+         break;
+       case 10:
+         BktPtr = &Char0110[0];// assosciate the pointer to the Sat2 array
+         break;
+       case 11:
+         BktPtr = &Char0111[0];// assosciate the pointer to the Sat3 array
+         break;
+       case 12:
+         BktPtr = &Char0112[0];// assosciate the pointer to the Sat4 array
+         break;
+       case 13:
+        BktPtr = &Char0113[0];// assosciate the pointer to the Sat1 array
+         break;
+       case 14:
+         BktPtr = &Char0114[0];// assosciate the pointer to the Sat2 array
+         break;
+       case 15:
+         BktPtr = &Char0115[0];// assosciate the pointer to the Sat3 array
+         break;
+       case 16:
+         BktPtr = &Char0116[0];// assosciate the pointer to the Sat4 array
+         break;
+     }
+ return BktPtr;
+}
+
+
+
+


Remove and add smoe stuff

Remove and add smoe stuff

--- blinky-tape/src/TestStatus.ino
+++ blinky-tape/src/TestStatus.ino
@@ -13,7 +13,11 @@
 unsigned long currentMillis;

 int charToInt(char c){
-  return (char)c;
+  int i = (int) c;
+  if(i < 48 || 58 < i){
+    return -1;
+  }
+  return (i - 48) * 6;
 }

 void decLevel(){
@@ -60,6 +64,9 @@
 void loop(){
   while(Serial.available() > 0) {
     int level = charToInt(Serial.read());
+    if(level < 0){
+      continue;
+    }
     setLevel(level);
   }

@@ -69,7 +76,6 @@
     previousMillis += INTERVAL;
     updateActualLevel();
     rainbow();
-    Serial.println(mLevel);
   }
 }


Compiles with RFM23B instance

Compiles with RFM23B instance

--- Arduino/hardware/V0p2_Main_PCB_REV7_DORM1_and_REV8/testsuite/201611/REV7Minimal/REV7Minimal.ino
+++ Arduino/hardware/V0p2_Main_PCB_REV7_DORM1_and_REV8/testsuite/201611/REV7Minimal/REV7Minimal.ino
@@ -20,18 +20,65 @@
  * Aim is to:
  *     - todo init GPIO pins to safe mode.
  *     - todo init peripherals to safe low power mode.
- *     - todo loop endlessly.
+ *     - loop endlessly.
  */

 // INCLUDES & DEFINES
-
+// REV7 / DORM1 all-in-one valve unit, secure TX.
+#define CONFIG_DORM1
+// Get defaults for valve applications.
+#include <OTV0p2_valve_ENABLE_defaults.h>
+// All-in-one valve unit (DORM1).
+#include <OTV0p2_CONFIG_REV7.h>
+// OTV0p2Base Libraries
+#include <OTV0p2Base.h>
+// Radio Libraries
+//#include <OTRadioLink.h>
+#include <OTRFM23BLink.h>

 // OBJECTS & VARIABLES
+/**
+ * Peripherals present on REV7
+ * - Pot        Set input to Hi-Z?
+ * - PHT        IO_POWER_UP LOW
+ * - Encoder    IO_POWER_UP LOW
+ * - LED        Set pin HIGH?
+ * - Button     Set to INPUT
+ * - H-Bridge   Control pins HIGH, Current sense set to input.
+ * - SHT21      read() once.
+ * - RFM23B     ??
+ * - XTAL       Setup and leave running?
+ * - UART       Disable
+ */
+
+/*
+ * Radio instance
+ */
+static constexpr bool RFM23B_allowRX = false;
+
+static constexpr uint8_t RFM23B_RX_QUEUE_SIZE = OTRFM23BLink::DEFAULT_RFM23B_RX_QUEUE_CAPACITY;
+static constexpr int8_t RFM23B_IRQ_PIN = -1;// PIN_RFM_NIRQ;
+// XXX Is it really worth having a separate primary radio in this case?
+OTRFM23BLink::OTRFM23BLink<OTV0P2BASE::V0p2_PIN_SPI_nSS, RFM23B_IRQ_PIN, RFM23B_RX_QUEUE_SIZE, RFM23B_allowRX> PrimaryRadio;//RFM23B;
+///* constexpr */ OTRadioLink::OTRadioLink &PrimaryRadio = RFM23B
+
+/*
+ * SHT21 instance
+ */

 // FUNCTIONS
+/**
+ * @brief   Set pins and on-board peripherals to safe low power state.
+ */
+
+/**
+ * @brief   Run POST.
+ */
+
+
 /**
  * @brief   Initialise GPIO pins and peripherals to a safe and low power mode.
  */


Put in template

Put in template

--- Arduino/hardware/V0p2_Main_PCB_REV7_DORM1_and_REV8/REV7RadValve/REV7RadValve.ino
+++ Arduino/hardware/V0p2_Main_PCB_REV7_DORM1_and_REV8/REV7RadValve/REV7RadValve.ino
@@ -17,6 +17,9 @@
                            Deniz Erbilgin 2015--2017
 */

+/******************************************************************************
+ * NOTES
+ *****************************************************************************/
 /*
   V0p2 (V0.2) core.

@@ -30,42 +33,93 @@
   Basic AVR power consumption ticking an (empty) control loop at ~0.5Hz should be ~1uA.
  */

-#include "V0p2_Main.h"
-#include <OTAESGCM.h>
-
-// Indicate that the system is broken in an obvious way (distress flashing the main LED).
-// DOES NOT RETURN.
-// Tries to turn off most stuff safely that will benefit from doing so, but nothing too complex.
-// Tries not to use lots of energy so as to keep distress beacon running for a while.
-void panic() {
-    // Reset radio and go into low-power mode.
-    PrimaryRadio.panicShutdown();
-    // Power down almost everything else...
-    OTV0P2BASE::minimisePowerWithoutSleep();
-    pinMode(OTV0P2BASE::LED_HEATCALL_L, OUTPUT);
-    for( ; ; ) {
-        OTV0P2BASE::LED_HEATCALL_ON();
-        OTV0P2BASE::nap(WDTO_15MS);
-        OTV0P2BASE::LED_HEATCALL_OFF();
-        OTV0P2BASE::nap(WDTO_120MS);
-    }
-}
-
-// Panic with fixed message.
-void panic(const __FlashStringHelper *s) {
-    OTV0P2BASE::serialPrintlnAndFlush(); // Start new line to highlight error.  // May fail.
-    OTV0P2BASE::serialPrintAndFlush('!'); // Indicate error with leading '!' // May fail.
-    OTV0P2BASE::serialPrintlnAndFlush(s); // Print supplied detail text. // May fail.
-    panic();
-}
-
+
+/******************************************************************************
+ * INCLUDES
+ *****************************************************************************/
+// FIXME once V0p2_Main.h removed
+//////// GLOBAL flags that alter system build and behaviour.
+//
+//// If defined, do extra checks and serial logging.  Will take more code space and power.
+//#undef DEBUG
+//// Ensure that OpenTRV 'standard' UART speed is set unless explicitly overridden.
+//#define BAUD 4800
+//
+//// *** Global flag for REVx configuration here *** //
+//// e.g.
+//// #define CONFIG_REV10_SECURE_BHR // REV10: secure stats relay and boiler hub.
+//
+//// Get defaults for valve applications.
+//#include <OTV0p2_valve_ENABLE_defaults.h>
+//
+//// *** Main board config imported here *** //
+//
+//// --------------------------------------------
+//// Fixups to apply after loading the target config.
+//#include <OTV0p2_valve_ENABLE_fixups.h>
+//// I/O pin allocation and setup: include ahead of I/O module headers.
+//#include <OTV0p2_Board_IO_Config.h>
+//
+//
+//////// MAIN LIBRARIES
+//
+//#include <Arduino.h>
+//#include <OTV0p2Base.h>
+//#include <OTRadioLink.h>
+
+
+////// ADDITIONAL LIBRARIES/PERIPHERALS
+
+#include "V0p2_Main.h"  // FIXME remove dependency
+// #define RFM23B_IRQ_CONTROL  // Enable RFM23B IRQ control code.
+// #include <OTRFM23BLink.h>
+ #include <OTAESGCM.h>
+
+
+////// ADDITIONAL USER HEADERS
+
+
+/******************************************************************************
+ * GENERAL CONSTANTS AND VARIABLES
+ * Core constants and variables required for V0p2 loop.
+ *****************************************************************************/
+// Controller's notion/cache of seconds within major cycle.
+static uint_fast8_t TIME_LSD;
+
+// 'Elapsed minutes' count of minute/major cycles; cheaper than accessing RTC and not tied to real time.
+// Starts at or just above zero (within the first 4-minute cycle) to help avoid collisions between units after mass power-up.
+// Wraps at its maximum (0xff) value.
+static uint8_t minuteCount;
+
+
+/******************************************************************************
+ * PERIPHERALS
+ * Peripheral drivers and config
+ *****************************************************************************/
+
+////// RADIOS
+
+// Config
 // Nodes talking on fast GFSK channel 0.
 static constexpr uint8_t nPrimaryRadioChannels = 1;
 static const OTRadioLink::OTRadioChannelConfig RFM23BConfigs[nPrimaryRadioChannels] = {
     // GFSK channel 0 full config, RX/TX, not in itself secure.
     OTRadioLink::OTRadioChannelConfig(OTRFM23BLink::StandardRegSettingsGFSK57600, true), };

-/////// SENSORS
+// Brings in necessary radio libs.
+static constexpr uint8_t RFM23B_RX_QUEUE_SIZE = OTV0P2BASE::fnmax(uint8_t(2), uint8_t(OTRFM23BLink::DEFAULT_RFM23B_RX_QUEUE_CAPACITY)) - 1;
+static constexpr int8_t RFM23B_IRQ_PIN = PIN_RFM_NIRQ;
+static constexpr bool RFM23B_allowRX = false;
+OTRFM23BLink::OTRFM23BLink<OTV0P2BASE::V0p2_PIN_SPI_nSS, RFM23B_IRQ_PIN, RFM23B_RX_QUEUE_SIZE, RFM23B_allowRX> RFM23B;
+
+// Assigns radio to PrimaryRadio alias
+OTRadioLink::OTRadioLink &PrimaryRadio = RFM23B;
+
+// When RX not enabled, switch in dummy version (base class implements stubs)
+OTRadioLink::OTMessageQueueHandlerNull messageQueue;  // fixme delete
+
+
+////// SENSORS

 // Sensor for supply (eg battery) voltage in millivolts.
 OTV0P2BASE::SupplyVoltageCentiVolts Supply_cV;
@@ -80,7 +134,8 @@
 // Ambient/room temperature sensor, usually on main board.
 OTV0P2BASE::RoomTemperatureC16_SHT21 TemperatureC16; // SHT21 impl.

-////////////////////////// Actuators
+
+////// ACTUATORS

 // DORM1/REV7 direct drive actuator.
 // Singleton implementation/instance.
@@ -88,7 +143,8 @@
 // unless recent UI use because value is being fitted/adjusted.
 ValveDirect_t ValveDirect([](){return((!valveUI.veryRecentUIControlUse()) && AmbLight.isRoomDark());});

-////////////////////////// CONTROL
+
+////// CONTROL

 // Singleton non-volatile stats store instance.
 OTV0P2BASE::EEPROMByHourByteStats eeStats;
@@ -110,25 +166,7 @@

 // Singleton implementation for entire node.
 OccupancyTracker Occupancy;
-/////// RADIOS
-
-// Brings in necessary radio libs.
-static constexpr uint8_t RFM23B_RX_QUEUE_SIZE = OTV0P2BASE::fnmax(uint8_t(2), uint8_t(OTRFM23BLink::DEFAULT_RFM23B_RX_QUEUE_CAPACITY)) - 1;
-static constexpr int8_t RFM23B_IRQ_PIN = PIN_RFM_NIRQ;
-static constexpr bool RFM23B_allowRX = false;
-OTRFM23BLink::OTRFM23BLink<OTV0P2BASE::V0p2_PIN_SPI_nSS, RFM23B_IRQ_PIN, RFM23B_RX_QUEUE_SIZE, RFM23B_allowRX> RFM23B;
-
-// Assigns radio to PrimaryRadio alias
-OTRadioLink::OTRadioLink &PrimaryRadio = RFM23B;
-
-// RFM22 is apparently SPI mode 0 for Arduino library pov.
-
-// When RX not enabled, switch in dummy version (base class implements stubs)
-OTRadioLink::OTMessageQueueHandlerNull messageQueue;
-
-//========================================
-// STUFF
-//========================================
+
 static OTV0P2BASE::EEPROMByHourByteStats ebhs;
 // Create setback lockout if needed.
 typedef bool(*setbackLockout_t)();
@@ -170,18 +208,15 @@
   OTV0P2BASE::LED_HEATCALL_OFF,
   OTV0P2BASE::LED_HEATCALL_ON_ISR_SAFE);

-
-// Controller's notion/cache of seconds within major cycle.
-static uint_fast8_t TIME_LSD;
-
-// 'Elapsed minutes' count of minute/major cycles; cheaper than accessing RTC and not tied to real time.
-// Starts at or just above zero (within the first 4-minute cycle) to help avoid collisions between units after mass power-up.
-// Wraps at its maximum (0xff) value.
-static uint8_t minuteCount;
+////// MESSAGING

 // Managed JSON stats.
 OTV0P2BASE::SimpleStatsRotation<12> ss1; // Configured for maximum different stats.  // FIXME REDUCE AS MUCH AS POSSIBLE

+
+/******************************************************************************
+ * INTERRUPT SERVICE ROUTINES
+ *****************************************************************************/

 // Previous state of port D pins to help detect changes.
 static volatile uint8_t prevStatePD;
@@ -201,6 +236,114 @@
     if((changes & SERIALRX_INT_MASK) && !(pins & SERIALRX_INT_MASK)) { OTV0P2BASE::CLI::resetCLIActiveTimer(); }
 }

+
+/******************************************************************************
+ * LOCAL FUNCTIONS
+ *****************************************************************************/
+
+////// PANIC
+
+// Indicate that the system is broken in an obvious way (distress flashing the main LED).
+// DOES NOT RETURN.
+// Tries to turn off most stuff safely that will benefit from doing so, but nothing too complex.
+// Tries not to use lots of energy so as to keep distress beacon running for a while.
+void panic() {
+    // Reset radio and go into low-power mode.
+    PrimaryRadio.panicShutdown();
+    // Power down almost everything else...
+    OTV0P2BASE::minimisePowerWithoutSleep();
+    pinMode(OTV0P2BASE::LED_HEATCALL_L, OUTPUT);
+    for( ; ; ) {
+        OTV0P2BASE::LED_HEATCALL_ON();
+        OTV0P2BASE::nap(WDTO_15MS);
+        OTV0P2BASE::LED_HEATCALL_OFF();
+        OTV0P2BASE::nap(WDTO_120MS);
+    }
+}
+
+// Panic with fixed message.
+void panic(const __FlashStringHelper *s) {
+    OTV0P2BASE::serialPrintlnAndFlush(); // Start new line to highlight error.  // May fail.
+    OTV0P2BASE::serialPrintAndFlush('!'); // Indicate error with leading '!' // May fail.
+    OTV0P2BASE::serialPrintlnAndFlush(s); // Print supplied detail text. // May fail.
+    panic();
+}
+
+
+////// DIAGNOSTICS
+
+#if 1
+// More detailed stack usage output
+inline void stackCheck()
+{
+    // Force restart if SPAM/heap/stack likely corrupt.
+    OTV0P2BASE::MemoryChecks::forceResetIfStackOverflow();
+
+    // Print max stack usage each cycle
+    const int16_t minsp = OTV0P2BASE::MemoryChecks::getMinSPSpaceBelowStackToEnd();
+    const uint8_t location = OTV0P2BASE::MemoryChecks::getLocation();
+    OTV0P2BASE::serialPrintAndFlush(F("minsp: "));
+    OTV0P2BASE::serialPrintAndFlush(minsp, HEX);
+    OTV0P2BASE::serialPrintAndFlush(F(" loc:"));
+    OTV0P2BASE::serialPrintAndFlush(location);
+    OTV0P2BASE::serialPrintlnAndFlush();
+
+    OTV0P2BASE::MemoryChecks::resetMinSP();
+}
+#endif
+
+////// SENSORS
+
+// Update sensors with historic/trailing statistics information where needed.
+// Should be called at least hourly after all stats have been updated,
+// but can also be called whenever the user adjusts settings for example.
+void updateSensorsFromStats() {
+    // Update with rolling stats to adapt to sensors and local environment...
+    // ...and prevailing bias, so may take a while to adjust.
+    AmbLight.setTypMinMax(
+          eeStats.getByHourStatRTC(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
+          eeStats.getMinByHourStat(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
+          eeStats.getMaxByHourStat(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
+          !tempControl.hasEcoBias());
+}
+
+
+////// CONTROL
+
+// Call this to do an I/O poll if needed; returns true if something useful definitely happened.
+// This call should typically take << 1ms at 1MHz CPU.
+// Does not change CPU clock speeds, mess with interrupts (other than possible brief blocking), or sleep.
+// Should also do nothing that interacts with Serial.
+// Limits actual poll rate to something like once every 8ms, unless force is true.
+//   * force if true then force full poll on every call (ie do not internally rate-limit)
+// Note that radio poll() can be for TX as well as RX activity.
+// Not thread-safe, eg not to be called from within an ISR.
+// FIXME trying to move into utils (for the time being.)
+bool pollIO(const bool force) {
+    static volatile uint8_t _pO_lastPoll;
+    // Poll RX at most about every ~8ms.
+    const uint8_t sct = OTV0P2BASE::getSubCycleTime();
+    if(force || (sct != _pO_lastPoll)) {
+        _pO_lastPoll = sct;
+        // Poll for inbound frames.
+        // If RX is not interrupt-driven then
+        // there will usually be little time to do this
+        // before getting an RX overrun or dropped frame.
+        PrimaryRadio.poll();
+    }
+    return(false);
+}
+
+// Run tasks needed at the end of each day (nominal midnight).
+// Should be run once at a fixed slot in the last minute of the last hour of each day.
+// Will be run after all stats for the current hour have been updated.
+static void endOfDayTasks() {
+    // Count down the setback lockout if not finished...  (TODO-786, TODO-906)
+    OTRadValve::countDownSetbackLockout();
+}
+
+
+////// MESSAGING

 // Do bare stats transmission.
 // Output should be filtered for items appropriate
@@ -329,62 +472,7 @@
 }

-
-//========================================
-// FUNCTIONS
-//========================================
-/////////  CONTROL
-
-// Call this to do an I/O poll if needed; returns true if something useful definitely happened.
-// This call should typically take << 1ms at 1MHz CPU.
-// Does not change CPU clock speeds, mess with interrupts (other than possible brief blocking), or sleep.
-// Should also do nothing that interacts with Serial.
-// Limits actual poll rate to something like once every 8ms, unless force is true.
-//   * force if true then force full poll on every call (ie do not internally rate-limit)
-// Note that radio poll() can be for TX as well as RX activity.
-// Not thread-safe, eg not to be called from within an ISR.
-// FIXME trying to move into utils (for the time being.)
-bool pollIO(const bool force) {
-    static volatile uint8_t _pO_lastPoll;
-    // Poll RX at most about every ~8ms.
-    const uint8_t sct = OTV0P2BASE::getSubCycleTime();
-    if(force || (sct != _pO_lastPoll)) {
-        _pO_lastPoll = sct;
-        // Poll for inbound frames.
-        // If RX is not interrupt-driven then
-        // there will usually be little time to do this
-        // before getting an RX overrun or dropped frame.
-        PrimaryRadio.poll();
-    }
-    return(false);
-}
-
-// Run tasks needed at the end of each day (nominal midnight).
-// Should be run once at a fixed slot in the last minute of the last hour of each day.
-// Will be run after all stats for the current hour have been updated.
-static void endOfDayTasks() {
-    // Count down the setback lockout if not finished...  (TODO-786, TODO-906)
-    OTRadValve::countDownSetbackLockout();
-}
-
-////////// SENSORS
-
-// Update sensors with historic/trailing statistics information where needed.
-// Should be called at least hourly after all stats have been updated,
-// but can also be called whenever the user adjusts settings for example.
-void updateSensorsFromStats() {
-    // Update with rolling stats to adapt to sensors and local environment...
-    // ...and prevailing bias, so may take a while to adjust.
-    AmbLight.setTypMinMax(
-          eeStats.getByHourStatRTC(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
-          eeStats.getMinByHourStat(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
-          eeStats.getMaxByHourStat(OTV0P2BASE::NVByHourByteStatsBase::STATS_SET_AMBLIGHT_BY_HOUR_SMOOTHED),
-          !tempControl.hasEcoBias());
-}
-
-
-
-///////// CLI
+////// UI

 // Dump some brief CLI usage instructions to serial TX, which must be up and running.
 // If this gets too big there is a risk of overrunning and missing the next tick...
@@ -470,10 +558,9 @@
 }

-
-//========================================
-// SETUP
-//========================================
+/******************************************************************************
+ * SETUP
+ *****************************************************************************/

 // Setup routine: runs once after reset.
 // Does some limited board self-test and will panic() if anything is obviously broken.
@@ -577,28 +664,10 @@
     TIME_LSD = OTV0P2BASE::getSecondsLT();
 }

-//========================================
-// MAIN LOOP
-//========================================
-#if 1
-// More detailed stack usage output
-inline void stackCheck()
-{
-	// Force restart if SPAM/heap/stack likely corrupt.
-    OTV0P2BASE::MemoryChecks::forceResetIfStackOverflow();
-
-    // Print max stack usage each cycle
-    const int16_t minsp = OTV0P2BASE::MemoryChecks::getMinSPSpaceBelowStackToEnd();
-    const uint8_t location = OTV0P2BASE::MemoryChecks::getLocation();
-    OTV0P2BASE::serialPrintAndFlush(F("minsp: "));
-    OTV0P2BASE::serialPrintAndFlush(minsp, HEX);
-    OTV0P2BASE::serialPrintAndFlush(F(" loc:"));
-    OTV0P2BASE::serialPrintAndFlush(location);
-    OTV0P2BASE::serialPrintlnAndFlush();
-
-    OTV0P2BASE::MemoryChecks::resetMinSP();
-}
-#endif
+
+/******************************************************************************
+ * MAIN LOOP
+ *****************************************************************************/

 void loop()
 {
@@ -840,3 +909,4 @@
 #endif
 #endif
 }
+


Cleanup

Cleanup

--- skypointer.ino
+++ skypointer.ino
@@ -227,12 +227,12 @@
 void ProcessReadEEPROM () {
   // Reads 12 bytes from EEPROM and sends them via Serial port.
   char buf[52];
-  uint8_t reads[12];
+  uint8_t datum[12];
   for (int k = 0; k < 12; k++) {
-    reads[k] = EEPROM.read(k);
+    datum[k] = EEPROM.read(k);
   }
   // Fill the buffer with the read data
-  sprintf(buf, "R %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d\r", reads[0], reads[1], reads[2], reads[3], reads[4], reads[5], reads[6], reads[7], reads[8], reads[9], reads[10], reads[11]);
+  sprintf(buf, "R %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d %03d\r", datum[0], datum[1], datum[2], datum[3], datum[4], datum[5], datum[6], datum[7], datum[8], datum[9], datum[10], datum[11]);
   Serial.print(buf);
 }


Example: change the type of the json string from char* to char[] because it cause issue in memory protected environments.

--- examples/JsonParserExample/JsonParserExample.ino
+++ examples/JsonParserExample/JsonParserExample.ino
@@ -1,94 +1,94 @@
-/*
-* malloc-free JSON parser for Arduino
-* Benoit Blanchon 2014 - MIT License
-*/
-
-#include <JsonParser.h>
-
-void ParseAnObject()
-{
-    char* json = "{\"Name\":\"Blanchon\",\"Skills\":[\"C\",\"C++\",\"C#\"],\"Age\":32,\"Online\":true}";
-
-    JsonParser<32> parser;
-
-    Serial.print("Parse ");
-    Serial.println(json);
-
-    JsonHashTable hashTable = parser.parseHashTable(json);
-
-    if (!hashTable.success())
-    {
-        Serial.println("JsonParser.parseHashTable() failed");
-        return;
-    }
-
-    char* name = hashTable.getString("Name");
-    Serial.print("name=");
-    Serial.println(name);
-
-    JsonArray skills = hashTable.getArray("Skills");
-    Serial.println("skills:");
-    for (int i = 0; i < skills.getLength(); i++)
-    {
-        char* value = skills.getString(i);
-        Serial.print(i);
-        Serial.print(" ");
-        Serial.println(value);
-    }
-
-    int age = hashTable.getLong("Age");
-    Serial.print("age=");
-    Serial.println(age);
-
-    bool online = hashTable.getBool("Online");
-    Serial.print("online=");
-    Serial.println(online);
-}
-
-void ParseAnArray()
-{
-    char* json = "[[1.2,3.4],[5.6,7.8]]";
-
-    JsonParser<32> parser;
-
-    Serial.print("Parse ");
-    Serial.println(json);
-
-    JsonArray array = parser.parseArray(json);
-
-    if (!array.success())
-    {
-        Serial.println("JsonParser.parseArray() failed");
-        return;
-    }
-
-    for (int i = 0; i < array.getLength(); i++)
-    {
-        Serial.println(i);
-
-        JsonArray innerArray = array.getArray(i);
-
-        for (int j = 0; j < innerArray.getLength(); j++)
-        {
-            double value = innerArray.getDouble(j);
-
-            Serial.print("  ");
-            Serial.print(j);
-            Serial.print("=");
-            Serial.println(value);
-        }
-    }
-}
-
-void setup()
-{
-    Serial.begin(9600);
-
-    ParseAnObject();
-    ParseAnArray();
-}
-
-void loop()
-{
-
-}
+/*
+* malloc-free JSON parser for Arduino
+* Benoit Blanchon 2014 - MIT License
+*/
+
+#include <JsonParser.h>
+
+void ParseAnObject()
+{
+    char[] json = "{\"Name\":\"Blanchon\",\"Skills\":[\"C\",\"C++\",\"C#\"],\"Age\":32,\"Online\":true}";
+
+    JsonParser<32> parser;
+
+    Serial.print("Parse ");
+    Serial.println(json);
+
+    JsonHashTable hashTable = parser.parseHashTable(json);
+
+    if (!hashTable.success())
+    {
+        Serial.println("JsonParser.parseHashTable() failed");
+        return;
+    }
+
+    char* name = hashTable.getString("Name");
+    Serial.print("name=");
+    Serial.println(name);
+
+    JsonArray skills = hashTable.getArray("Skills");
+    Serial.println("skills:");
+    for (int i = 0; i < skills.getLength(); i++)
+    {
+        char* value = skills.getString(i);
+        Serial.print(i);
+        Serial.print(" ");
+        Serial.println(value);
+    }
+
+    int age = hashTable.getLong("Age");
+    Serial.print("age=");
+    Serial.println(age);
+
+    bool online = hashTable.getBool("Online");
+    Serial.print("online=");
+    Serial.println(online);
+}
+
+void ParseAnArray()
+{
+    char[] json = "[[1.2,3.4],[5.6,7.8]]";
+
+    JsonParser<32> parser;
+
+    Serial.print("Parse ");
+    Serial.println(json);
+
+    JsonArray array = parser.parseArray(json);
+
+    if (!array.success())
+    {
+        Serial.println("JsonParser.parseArray() failed");
+        return;
+    }
+
+    for (int i = 0; i < array.getLength(); i++)
+    {
+        Serial.println(i);
+
+        JsonArray innerArray = array.getArray(i);
+
+        for (int j = 0; j < innerArray.getLength(); j++)
+        {
+            double value = innerArray.getDouble(j);
+
+            Serial.print("  ");
+            Serial.print(j);
+            Serial.print("=");
+            Serial.println(value);
+        }
+    }
+}
+
+void setup()
+{
+    Serial.begin(9600);
+
+    ParseAnObject();
+    ParseAnArray();
+}
+
+void loop()
+{
+
+}


Skeleton of sketch that will be running.

--- arduino/bubbles_controller/bubbles_controller.ino
+++ arduino/bubbles_controller/bubbles_controller.ino
@@ -1,24 +1,84 @@
-#include <Process.h>
+/* bubbles_controller
+*
+*  copyright Becky Stewart, Anti-Alias Labs
+*  becky@antialiaslabs.com
+*
+*  For the Arduino Yun to be run on the microcontoller
+*  while tweet-contoller.py runs on the Linino.
+*
+*  Bubbles are triggered through following ways:
+*  1. A tweet has the hashtag #teambubble
+*  2. It has been 15 minutes since the last tweet
+*       (need to keep water moving)
+*/

-Process twitter;     // process to read tweets
+#include <Bridge.h>

+// pins
+int greenStatusLED = 6;
+int yellowStatusLED = 5;
+int relay1 = 2;
+int relay2 = 3;
+
+// other variables
+int bubbleTime = 150;
+int bubbleThrottle = 5000;
+
+char tweetValue[2];    // incoming storage of tweet
+int lastTweetCount = 0; // keep track of number of tweets
+unsigned long lastBubble;
+
+//---------------------------------------------
 void setup() {
   Bridge.begin();    // initialise Bridge
-  Serial.begin(9600);   // initialise serial

-  while (!Serial);  // wait for Serial Monitor to open
-  Serial.println( "Welcome to the BubblinO2" );
+  // set up pin modes
+  pinMode( greenStatusLED, OUTPUT );
+  pinMode( yellowStatusLED, OUTPUT );
+  pinMode( relay1, OUTPUT );
+  pinMode( relay2, OUTPUT );

-  // run the Python script on the Linino
-  twitter.runShellCommend( "python /usr/bubblino2/linino/tweet-controller.py" );
+  // initialise the timer for the last bubble
+  lastBubble = millis();
 }

+//---------------------------------------------
 void loop() {
   // Read command output
-  while (twitter.available()) {
-    int result = twitter.parseInt();			// look for an integer
-    Serial.println(result);			// print the number as well
-  }
+  Bridge.get("tweets", tweetValue, 2);
+  int tweets = atoi(tweetValue);
+
+
   delay(5000);  // wait 5 seconds before you do it again

+  // startup bubble
+  bubble();
 }
+
+//---------------------------------------------
+void bubble() {
+  // turn on status LED
+  digitalWrite( greenStatusLED, HIGH );
+  digitalWrite( yellowStatusLED, LOW );
+
+  // trigger relay
+  digitalWrite( relay1, HIGH );
+  digitalWrite( relay2, HIGH );
+
+  // wait to create bubbles
+  delay( bubbleTime );
+
+  // stop relay
+  digitalWrite( relay1, LOW );
+  digitalWrite( relay2, LOW );
+
+  // update status LEDs
+  digitalWrite( greenStatusLED, LOW);
+  digitalWrite( yellowStatusLED, HIGH);
+
+  // wait to throttle bubbling
+  delay( bubbleThrottle );
+
+  // initialise the timer for the last bubble
+  lastBubble = millis();
+}


correct StreamHttpClient.ino example

correct StreamHttpClient.ino example

--- libraries/ESP8266httpClient/examples/StreamHttpClient/StreamHttpClient.ino
+++ libraries/ESP8266httpClient/examples/StreamHttpClient/StreamHttpClient.ino
@@ -63,7 +63,7 @@
                 uint8_t buff[128] = { 0 };

                 // get tcp stream
-                WiFiClient * stream = http.getStream();
+                WiFiClient * stream = http.getStreamPtr();

                 // read all data from server
                 while(http.connected() && (len > 0 || len == -1)) {


Simplify the onewire calls.

Simplify the onewire calls.

--- src/sensor.ino
+++ src/sensor.ino
@@ -1,116 +1,68 @@
-// This #include statement was automatically added by the Spark IDE.
 #include "OneWire.h"

-float celsius;
-char cel[8] = "NONE";
-char far[8] = "NONE";
+uint8_t rom[8];
+uint8_t resp[9];
+char result[16] = "NONE";
+char device[16] = "NONE";
+
 int temp_sensor = D3;
+OneWire d3 = OneWire(temp_sensor);  // DS18B20 on pin D3

-OneWire ds = OneWire(temp_sensor);  // on pin D3 (a 4.7K resistor is necessary)
+#define publish_delay 60000
+unsigned int lastPublish = 0;

 void setup() {
-  Serial.begin(9600);
-  Spark.variable("cel",&cel,STRING);
-  Spark.variable("far",&far,STRING);
+  Spark.variable("result", &result, STRING);
+  Spark.variable("device", &device, STRING);
   pinMode(temp_sensor, INPUT);
 }

 void loop() {
-  byte i;
-  byte present = 0;
-  byte type_s;
-  byte data[12];
-  byte addr[8];
-  float celsius, fahrenheit;

-  if ( !ds.search(addr)) {
-    Serial.println("No more addresses.");
-    Serial.println();
-    ds.reset_search();
-    delay(5000);
-    ds.reset();
-    ds.skip();
-    ds.write(0x44);
-    Serial.println("Converting temp on all probes");
-    Serial.println();
-    delay(1000);
+  unsigned long now = millis();
+
+  if ((now - lastPublish) < publish_delay) {
     return;
   }

-  Serial.print("ROM =");
-  for( i = 0; i < 8; i++) {
-    Serial.write(' ');
-    Serial.print(addr[i], HEX);
-  }
+  d3.reset_search(); // Start back at the beginning
+  if ( !d3.reset() ) {
+    sprintf(device, "NO DEVICE");
+    delay(5000);
+    return;
+   }

-  if (OneWire::crc8(addr, 7) != addr[7]) {
-      Serial.println("CRC is not valid!");
-      return;
-  }
-  Serial.println();
+  d3.skip(); // no need to search, only 1 device on the bus
+  d3.write(0x44,1);  // start conversation, with parasite power on at the end
+  delay(1000);  // maybe 750ms is enough, maybe not

-  // the first ROM byte indicates which chip
-  switch (addr[0]) {
-    case 0x10:
-      Serial.println("  Chip = DS18S20");  // or old DS1820
-      type_s = 1;
-      break;
-    case 0x28:
-      Serial.println("  Chip = DS18B20");
-      type_s = 0;
-      break;
-    case 0x22:
-      Serial.println("  Chip = DS1822");
-      type_s = 0;
-      break;
-    default:
-      Serial.println("Device is not a DS18x20 family device.");
-      return;
-  }
+  // Get the ROM address
+  d3.reset();
+  d3.write(0x33);
+  d3.read_bytes(rom, 8);
+  // Get the temp
+  d3.reset();
+  d3.write(0x55);
+  d3.write_bytes(rom,8);
+  d3.write(0x44);
+  delay(10);
+  d3.reset();
+  d3.write(0x55);
+  d3.write_bytes(rom, 8);
+  d3.write(0xBE);
+  d3.read_bytes(resp, 9);

-  // start conversion, with parasite power on at the end
-  present = ds.reset();
-  ds.select(addr);
-  ds.write(0xBE);         // Read Scratchpad
+  byte MSB = resp[1];
+  byte LSB = resp[0];

-  Serial.print("  Data = ");
-  Serial.print(present, HEX);
-  Serial.print(" ");
-  for ( i = 0; i < 9; i++) {           // we need 9 bytes
-    data[i] = ds.read();
-    Serial.print(data[i], HEX);
-    Serial.print(" ");
-  }
-  Serial.print(" CRC=");
-  Serial.print(OneWire::crc8(data, 8), HEX);
-  Serial.println();
+  int16_t intTemp = ((MSB << 8) | LSB); //using two's compliment 16-bit
+  float celsius =   ((double)intTemp)/16.0;
+  float fahrenheit = (( celsius*9.0)/5.0+32.0);

-  // Convert the data to actual temperature
-  // because the result is a 16 bit signed integer, it should
-  // be stored to an "int16_t" type, which is always 16 bits
-  // even when compiled on a 32 bit processor.
-  int16_t raw = (data[1] << 8) | data[0];
-  if (type_s) {
-    raw = raw << 3; // 9 bit resolution default
-    if (data[7] == 0x10) {
-      // "count remain" gives full 12 bit resolution
-      raw = (raw & 0xFFF0) + 12 - data[6];
-    }
-  } else {
-    byte cfg = (data[4] & 0x60);
-    // at lower res, the low bits are undefined, so let's zero them
-    if (cfg == 0x00) raw = raw & ~7;  // 9 bit resolution, 93.75 ms
-    else if (cfg == 0x20) raw = raw & ~3; // 10 bit res, 187.5 ms
-    else if (cfg == 0x40) raw = raw & ~1; // 11 bit res, 375 ms
-    //// default is 12 bit resolution, 750 ms conversion time
-  }
-  celsius = (float)raw / 16.0;
-  sprintf(cel,"%f.1", celsius);
-  fahrenheit = celsius * 1.8 + 32.0;
-  sprintf(far,"%f.1", fahrenheit);
-  Serial.print("  Temperature = ");
-  Serial.print(celsius);
-  Serial.print(" Celsius, ");
-  Serial.print(fahrenheit);
-  Serial.println(" Fahrenheit");
+  sprintf(result, "%2.2f", fahrenheit);
+  sprintf(device, "%x%x%x%x%x%x%x%x", rom[0], rom[1],
+    rom[2], rom[3], rom[4], rom[5], rom[6], rom[7]);
+
+  Spark.publish(device, String(result), 60, PRIVATE);
+  lastPublish = now;
 }