Добавление функцмонала

Добавление функцмонала

--- main.ino
+++ main.ino
@@ -8,10 +8,19 @@
 #include <DS1307RTC.h>
 #include <LiquidCrystal_I2C.h>

+// #define FIRST_LOADING
+// #define DEBUG
+
+#define set_bit(m,b)	((m) |= (b))
+#define unset_bit(m,b)	((m) &= ~(b))
+#define bit_seted(m,b)	((b) == ((m) & (b)))
+
+#define byte_to_analog(x)	((int)(4.015 * x))
+#define analog_to_byte(x)	((byte)(0.248 * x))
+
 LiquidCrystal_I2C lcd(0x27,16,2); // Инициализация дисплея (адрес, количество символов, количество строк)

 #define VERSION "1.0(b)"
-#define DEBUG

 static byte	bat_icon[8] = {
 	B01110,
@@ -24,31 +33,30 @@
 	B11111
 };

+/*bits system_byte*/
+#define RED_SPEED			(1 << 0)	// Включать ли красный свет при уменьшении скорости
+#define AUTO_BACKLIGHT		(1 << 1)	// Включать подсветку экрана по датчику света или нет
+#define AUTO_HEADLIGHTS		(1 << 2)	// Включать фару по датчику света или нет
+#define AlARM_STATE			(1 << 3)	// Для того, чтобы даже после сброса сигнализация не выключилась
+#define NENON_ON_DOWNTIME	(1 << 4)	// Плавное свечение нижней подсветки в простое
+
 struct sys_conf {
-	int		password[6];		// Пароль, для отключения сигнала
-
-	int		button_ok,
+	byte	password[6],		// Пароль, для отключения сигнала
+			button_ok,
 			button_up,
 			button_down,
 			button_signal,
+			button_ok_signal,	// Комбинация кнопок для захода в инженерное меню
+			time_to_slpeep,		// Время, после которого компьютер уснёт (минуты)
+			system_byte,		// Байт взявший в себя функцию нескольких болевкских переменных
 			lux_light_on,		// При какой яркости включать фару
 			lux_backlight_on,	// При какой яркости включать подсветку экрана
 			lux_headlight;		// Яркость фары
-
-	bool	red_speed,			// Включать ли красный свет при уменьшении скорости
-			auto_backlight,		// Включать подсветку экрана по датчику света или нет
-			auto_headlights,	// Включать фару по датчику света или нет
-			alarm_state;		// Для того, чтобы даже после сброса сигнализация не выключилась
-
-	byte	time_to_slpeep,		// Время, после которого компьютер уснёт (минуты)

 	float	distance,
 			max_speed,
 			wheel_length;		// Длина колеса
 };
-
-/*Стандартные значения*/
-#define BIP_DELAY			4	// Сколько итераций пищать (* 500 / 10000)

 /*Аналоговые выводы*/
 #define ACTION_BUTTON		6
@@ -71,8 +79,23 @@
 #define RIGHT_TURN_LIGHT	1

 /*Системные макросы*/
-#define SWITCH_NEXT			150		// Врямя в мс до переключения на следующий пункт при зажатой кнопке
+#define SWITCH_NEXT			200		// Врямя в мс до переключения на следующий пункт при зажатой кнопке
 #define LONG_PRESS			2000	// Время долгого нажатия кнопки
+#define TURN_SIGNAL_DELAY	500		// Время задержки мигания поворотника
+
+/*Системные define*/
+#define	BUT_OK				1
+#define	BUT_UP				2
+#define	BUT_DOWN			3
+#define	BUT_SIGNAL			4
+
+/*bits turn_signals*/
+#define TURN_SIGNAL_ON		(1 << 0)
+#define TURN_SIGNAL_LEFT	(1 << 1)
+#define TURN_SIGNAL_RIGHT	(1 << 2)
+#define SIGNAL_LEFT_ON		(1 << 3)
+#define SIGNAL_RIGHT_ON		(1 << 4)
+#define EMERGENCY_SIGNAL	(1 << 5)

 unsigned long	lastturn;	// Время последнего обращения

@@ -80,25 +103,37 @@
 			distance		= 0.0;	// Расстояние

 byte		bat_percent		= 100,
-			system_state	= 0;
-
-#define SPEED_STATE			0
-#define AlARM_STATE			1
-#define MENU_STATE			2
-#define SLEEP_STATE			3
+			system_mode		= 0,
+			alarm_now		= false,
+			turn_signals;
+
+/*system_mode*/
+#define SPEED_MODE			0
+#define ALARM_MODE			1
+#define MENU_MODE			2
+#define SLEEP_MODE			3
+#define ENGINEERING_MODE	4

 sys_conf		btc_config; // Конфигурация системы

 void setup() {
+	#ifdef DEBUG
+	Serial.begin(9600);
+	#endif
+
+	pinMode(EXT_ALARM, OUTPUT);
+	digitalWrite(EXT_ALARM, HIGH);
+
 	pinMode(DISPLAY_LIGHT, OUTPUT);		// Подключение подсветки экрана
-
-	for (byte	i	= 0; i < 255; i++, delay(8), analogWrite(DISPLAY_LIGHT, i));

 	lcd.begin();
 	lcd.print("Loading system...");
 	lcd.setCursor(0, 1);
 	lcd.print("Version: ");
 	lcd.print(VERSION);
+
+	for (byte	i	= 0; i < 255; i++, delay(8), analogWrite(DISPLAY_LIGHT, i));
+

 	/*Инициализация цифровых выводов*/
 	pinMode(BIP, OUTPUT);
@@ -109,8 +144,7 @@
 	pinMode(RED_BACK_LIGHT, OUTPUT);
 	pinMode(DISPLAY_LIGHT, OUTPUT);
 	pinMode(DATA_PIN, OUTPUT);
-	pinMode(CLOCK_PIN, OUTPUT);
-	pinMode(EXT_ALARM, OUTPUT);
+	pinMode(CLOCK_PIN, OUTPUT);

 	setSyncProvider(RTC.get);			// Для времени

@@ -119,50 +153,193 @@
 	attachInterrupt(1, speed, CHANGE);

 	lcd.createChar(0, bat_icon);	// Загрузка иконки батареи
+
+	#ifdef DEBUG
+	lcd.clear();
+	lcd.print("Wait for serial");
+	lcd.setCursor(0, 1);
+	lcd.print("Input \"0\"");
+	while (Serial.available() != 0);
+	#endif
+
+	#ifdef FIRST_LOADING
+	btc_config	= {};
+	btc_config.time_to_slpeep	= 5;
+	set_bit(btc_config.system_byte, AUTO_BACKLIGHT);
+	calibration();
+	input_password();
+	WriteSysConfEEPROM(btc_config, 0);
+	#else
+	ReadSysConfEEPROM(&btc_config, 0);
+	#endif
+
+	#ifdef DEBUG
+	Serial.println("btc_config:");
+	Serial.print("btc_config.password[0]: ");
+	Serial.println(btc_config.password[0]);
+
+	Serial.print("btc_config.password[1]: ");
+	Serial.println(btc_config.password[1]);
+
+	Serial.print("btc_config.password[2]: ");
+	Serial.println(btc_config.password[2]);
+
+	Serial.print("btc_config.password[3]: ");
+	Serial.println(btc_config.password[3]);
+
+	Serial.print("btc_config.password[4]: ");
+	Serial.println(btc_config.password[4]);
+
+	Serial.print("btc_config.password[5]: ");
+	Serial.println(btc_config.password[5]);
+
+	Serial.print("btc_config.button_ok: ");
+	Serial.println(btc_config.button_ok);
+
+	Serial.print("btc_config.button_up: ");
+	Serial.println(btc_config.button_up);
+
+	Serial.print("btc_config.button_down: ");
+	Serial.println(btc_config.button_down);
+
+	Serial.print("btc_config.button_signal: ");
+	Serial.println(btc_config.button_signal);
+
+	Serial.print("btc_config.button_ok_signal: ");
+	Serial.println(btc_config.button_ok_signal);
+
+	Serial.print("btc_config.time_to_slpeep: ");
+	Serial.println(btc_config.time_to_slpeep);
+
+	Serial.print("btc_config.system_byte: ");
+	Serial.println(btc_config.system_byte);
+
+	Serial.print("btc_config.lux_light_on: ");
+	Serial.println(btc_config.lux_light_on);
+
+	Serial.print("btc_config.lux_backlight_on: ");
+	Serial.println(btc_config.lux_backlight_on);
+
+	Serial.print("btc_config.lux_headlight: ");
+	Serial.println(btc_config.lux_headlight);
+
+	Serial.print("btc_config.distance: ");
+	Serial.println(btc_config.distance);
+
+	Serial.print("btc_config.max_speed: ");
+	Serial.println(btc_config.max_speed);
+
+	Serial.print("btc_config.wheel_length: ");
+	Serial.println(btc_config.wheel_length);
+	#endif
+
+	if ((analogRead(ACTION_BUTTON) > (btc_config.button_ok_signal - 5)) && (analogRead(ACTION_BUTTON) > (btc_config.button_ok_signal - 5))) {
+		engineering_menu();
+	}
+
+	system_mode	= SPEED_MODE;
 }

 void loop() {
-
+	switch (system_mode) {
+		case SPEED_MODE:	road_mode();
+							break;
+
+		case ALARM_MODE:	break;
+
+		case MENU_MODE:		menu();
+							break;
+
+		case SLEEP_MODE:	break;
+
+		case ENGINEERING_MODE:	engineering_menu();
+								break;
+	}
 }

 void alarm() {
-
-}
-
-void speed() {
-
-}
-
-void sys_watch() {
-	if ((btc_config.auto_headlights) && (analogRead(LIGHT_SENSOR) > btc_config.lux_light_on)) {	// Следилка за фарой
+	alarm_now	= true;
+}
+
+void speed() {	// Подсчёт скорости
+	if ((millis() - lastturn) > 80) { // Защита от случайных измерений (основано на том, что велосипед не будет ехать быстрее 120 кмч)
+		speed_now	= btc_config.wheel_length / ((float)(millis() - lastturn) / 1000) * 3.6;	// Расчет скорости, км/ч
+		lastturn	= millis();	// Запомнить время последнего оборота
+		distance	= distance + btc_config.wheel_length / 1000;	// Прибавляем длину колеса к дистанции при каждом обороте
+	}
+}
+
+void(* resetFunc) (void) = 0; // Функция сброса arduino
+
+bool sys_watch() {
+	if ((bit_seted(btc_config.system_byte, AUTO_HEADLIGHTS)) && (analogRead(LIGHT_SENSOR) > btc_config.lux_light_on)) {	// Следилка за фарой
 		digitalWrite(HEADLIGHT, LOW);
 	} else {
-		digitalWrite(HEADLIGHT, HIGH);
-	}
-
-	if ((btc_config.auto_b) && (analogRead(LIGHT_SENSOR) > btc_config.lux_light_on)) {	// Следилка за фарой
+		analogWrite(HEADLIGHT, btc_config.lux_headlight);
+	}
+
+	if ((bit_seted(btc_config.system_byte, AUTO_BACKLIGHT)) && (analogRead(LIGHT_SENSOR) > btc_config.lux_backlight_on)) {	// Следилка за фарой
 		digitalWrite(DISPLAY_LIGHT, LOW);
-}
-
-unsigned int key_pressed(bool wait_keys /*Надо ли ожидать кнопку бесконечно*/) {	// Определение нажатой кнопки
-	int		key,
-			delay_time	= 0;	// Время зажатия кнопки
-
-	while (sys_watch()) {
-
-		key	= analogRead(ACTION_BUTTON);
-
-		if ((key >= btc_config.button_ok - 5) && (key <= btc_config.button_ok + 5)) {
-			key = btc_config.button_ok;
+	} else {
+		digitalWrite(DISPLAY_LIGHT, LOW);
+	}
+
+	return true;
+}
+
+byte key_pressed(bool wait_keys /*Надо ли ожидать кнопку бесконечно*/) {	// Определение нажатой кнопки
+	int		key_now;
+	byte	delay_time	= 0;	// Время зажатия кнопки
+
+	while (true) {
+
+		if (!sys_watch()) return 0;
+
+		key_now	= analogRead(ACTION_BUTTON);
+
+		#ifdef DEBUG
+		Serial.println("****");
+		Serial.print("Key pressed: ");
+		Serial.println(key_now);
+		#endif
+
+		if (key_now < 5) {
+			if (!wait_keys) {
+				break;
+			} else {
+				continue;
+			}
+		}
+
+		key_now	= analog_to_byte(key_now);
+
+		#ifdef DEBUG
+		Serial.println(key_now);
+		#endif
+
+		if ((key_now >= btc_config.button_ok - 5) && (key_now <= btc_config.button_ok + 5)) {
+			key_now = BUT_OK;
+			#ifdef DEBUG
+			Serial.println("Pressed key ok");
+			#endif
 			break;
-		} else if ((key >= btc_config.button_up - 5) && (key <= btc_config.button_up + 5)) {
-			key = btc_config.button_up;
+		} else if ((key_now >= btc_config.button_up - 5) && (key_now <= btc_config.button_up + 5)) {
+			#ifdef DEBUG
+			Serial.println("Pressed key up");
+			#endif
+			key_now = BUT_UP;
 			break;
-		} else if ((key >= btc_config.button_down - 5) && (key <= btc_config.button_down + 5)) {
-			key = btc_config.button_down;
+		} else if ((key_now >= btc_config.button_down - 5) && (key_now <= btc_config.button_down + 5)) {
+			#ifdef DEBUG
+			Serial.println("Pressed key down");
+			#endif
+			key_now = BUT_DOWN;
 			break;
-		} else if ((key >= btc_config.button_signal - 5) && (key <= btc_config.button_signal + 5)) {
-			key = btc_config.button_signal;
+		} else if ((key_now >= btc_config.button_signal - 5) && (key_now <= btc_config.button_signal + 5)) {
+			#ifdef DEBUG
+			Serial.println("Pressed key signal");
+			#endif
+			key_now = BUT_SIGNAL;
 			break;
 		}

@@ -170,10 +347,594 @@
 			break;
 	}

-	while ((analogRead(ACTION_BUTTON) > 5) && (delay_time < SWITCH_NEXT)) {	// Ожидание зажатия
+	while ((wait_keys) && (analogRead(ACTION_BUTTON) > 5) && (delay_time < SWITCH_NEXT)) {	// Ожидание зажатия
 		delay(1);
 		delay_time++;
 	}

-	return key;
+	#ifdef DEBUG
+	Serial.println("****");
+	#endif
+
+	return key_now;
+}
+
+void about() {
+	lcd.clear();
+	lcd.print("BlueSparkProject");
+	lcd.setCursor(0, 1);
+	lcd.print(__DATE__);
+	lcd.print(" ");
+	lcd.print(__TIME__);
+	key_pressed(true);
+}
+
+void menu() {
+	char menu_array[][15]	= {
+		"Sleep",
+		"Speedometr",
+		"Stopwatch",
+		"System state",
+		"Settings"
+	};
+
+	while (system_mode == MENU_MODE) {
+		switch(display_list(menu_array, 5)) {
+			case 0:	break;
+
+			case 1:	system_mode	= SPEED_MODE;
+					break;
+
+			case 2:	break;
+
+			case 3:	break;
+
+			case 4:	settings();
+					break;
+		}
+	}
+}
+
+void settings() {
+	byte changes	= false,	// Для отслеживания изменений и последующей записи в EEPROM
+		 count = 0;
+
+	char setting_array[][15]	= {
+		"Blue light",
+		"Password",
+		"Light settings",
+		"Time setting",
+		"About system",
+		"Back"
+	};
+
+	while (true) {
+		switch (display_list(setting_array, 6)) {
+			case 0: if (digitalRead(LOWER_LIGHT) == HIGH) {
+						digitalWrite(LOWER_LIGHT, LOW);
+					} else {
+						digitalWrite(LOWER_LIGHT, HIGH);
+					}
+					break;
+
+			case 1:	while ((read_password() == false) && (count < 3)) {	// Счётчик количества неправильных вводов
+						count++;
+					}
+
+					if (count == 3) {
+						alarm_now	= true;
+					} else {
+						input_password();
+						changes	= true;
+					}
+					break;
+
+			case 2: break;
+
+			case 3:	TimeElements	t_n;
+					time_t			timeVal;
+					t_n.Second	= 0;
+					t_n.Hour	= input_int_number("Input hour", 0, 23);
+					t_n.Minute	= input_int_number("Input minutes", 0, 59);
+					t_n.Day		= input_int_number("Input day", 1, 31);
+					t_n.Month	= input_int_number("Input month", 1, 12);
+					t_n.Year	= input_int_number("Input year", 15, 20) + 30;
+					timeVal		= makeTime(t_n);
+					RTC.set(timeVal);
+					setTime(timeVal);
+					break;
+
+			case 4: about();
+					break;
+
+			case 5: return;
+					break;
+		}
+	}
+
+	if (changes) {
+		WriteSysConfEEPROM(btc_config, 0);
+	}
+}
+
+byte display_list(char list_array[][15], byte all_element) {
+	lcd.clear();
+
+	byte	selected		= 0,
+			on_display		= 0;
+
+	bool	key_pressed_ok	= true;
+
+	while (true) {
+		if (key_pressed_ok) {
+			if (selected == on_display) {
+				lcd.setCursor(0,0);
+				lcd.print(">");
+				lcd.setCursor(0,1);
+				lcd.print(" ");
+			} else {
+				lcd.setCursor(0,1);
+				lcd.print(">");
+				lcd.setCursor(0,0);
+				lcd.print(" ");
+			}
+
+			lcd.setCursor(1,0);
+			lcd.print(list_array[on_display]);
+
+			if (on_display + 1 < all_element) {
+				lcd.setCursor(1,1);
+				lcd.print(list_array[on_display + 1]);
+			}
+		}
+
+		key_pressed_ok	= true;
+
+		switch (key_pressed(true)) {
+			case BUT_OK:	return selected;
+							break;
+
+			case BUT_UP:	if (selected != 0) {
+								if (selected == on_display) {
+									lcd.clear();
+									on_display	-= 2;
+								}
+
+								selected--;
+							}
+							break;
+
+			case BUT_DOWN:	if (selected < all_element - 1) {
+								if (selected == (on_display + 1)) {
+									lcd.clear();
+									on_display	+= 2;
+								}
+
+								selected++;
+							}
+							break;
+
+			default:		key_pressed_ok	= false;
+		}
+	}
+}
+
+byte input_int_number(const char *text, byte min_num, byte max_num) {	// Ввод целочисленного числа
+	lcd.clear();
+	lcd.print(text);
+
+	byte	same_num = min_num;
+
+	while (true) {
+		lcd.setCursor(0, 1);
+		lcd.print("   ");
+
+		lcd.setCursor(0, 1);
+		lcd.print(same_num);
+
+		switch (key_pressed(true)) {
+			case BUT_UP:	if (same_num == max_num) {
+								same_num	= min_num;
+							} else {
+								same_num++;
+							}
+							break;
+
+			case BUT_DOWN:	if (same_num == min_num) {
+								same_num	= max_num;
+							} else {
+								same_num--;
+							}
+							break;
+
+			case BUT_OK:	return same_num;
+							break;
+		}
+	}
+}
+
+float input_float_number(char text[], float min_num, float max_num) {	// Ввод числа с точкой
+	lcd.clear();
+	lcd.print(text);
+
+	float	same_num = min_num;
+
+	while (true) {
+		lcd.setCursor(0, 1);
+		lcd.print("                ");
+		lcd.setCursor(0, 1);
+		lcd.print(same_num);
+
+		switch (key_pressed(true)) {
+			case BUT_UP:	if ((same_num + 0.1) > max_num) {
+									same_num	= min_num;
+							} else {
+								same_num	+= 0.1;
+							}
+							break;
+
+			case BUT_DOWN:	if ((same_num - 0.1) < min_num) {
+								same_num	= max_num;
+							} else {
+								same_num	-= 0.1;
+							}
+							break;
+
+			case BUT_OK:	return same_num;
+							break;
+		}
+	}
+}
+
+byte input_int_number(byte min_num, byte max_num) {	// Ввод целочисленного числа
+	byte	same_num = min_num;
+
+	lcd.setCursor(0, 1);
+	lcd.print("   ");
+
+	lcd.setCursor(0, 1);
+	lcd.print(same_num);
+
+	switch (key_pressed(true)) {
+		case BUT_UP:	if (same_num == max_num) {
+							same_num	= min_num;
+						} else {
+							same_num++;
+						}
+						break;
+
+		case BUT_DOWN:	if (same_num == min_num) {
+							same_num	= max_num;
+						} else {
+							same_num--;
+						}
+						break;
+
+		case BUT_OK:	return same_num;
+						break;
+	}
+}
+
+void registerWrite(int whichPin, int whichState) {
+	byte bitsToSend = 0;	// инициализируем и обнуляем байт
+
+	digitalWrite(8, LOW);	//Отключаем вывод на регистре
+	bitWrite(bitsToSend, whichPin, whichState);	// устанавливаем HIGH в соответствующем бите
+	shiftOut(11, 12, MSBFIRST, bitsToSend);	// проталкиваем байт в регистр
+	digitalWrite(8, HIGH);	// "защелкиваем" регистр, чтобы байт появился на его выходах
+}
+
+void registerWrite(byte bitsToSend) {
+	digitalWrite(8, LOW);	//Отключаем вывод на регистре
+	shiftOut(11, 12, MSBFIRST, bitsToSend);	// проталкиваем байт в регистр
+	digitalWrite(8, HIGH);	// "защелкиваем" регистр, чтобы байт появился на его выходах
+}
+
+void input_password() {
+	lcd.clear();			// Очистка экрана
+	lcd.print("New password");
+
+	lcd.setCursor(0, 1);	// Установка указателя в левый верхний угол
+	lcd.print("Password: ");
+
+	for (byte i = 0; i < 6; i++) {
+		btc_config.password[i]	= key_pressed(true);
+		lcd.print("*");
+	}
+
+	lcd.clear();
+	lcd.print("Complete!");
+	delay(2000);
+}
+
+bool read_password() {
+	bool	wrong = false;
+
+	lcd.clear();			// Очистка экрана
+	lcd.print("Current password");
+
+	lcd.setCursor(0, 1);	// Установка указателя в левый верхний угол
+	lcd.print("Password: ");
+
+	for (byte i = 0; i < 6; i++) {
+		if (btc_config.password[i]	!= key_pressed(true)) {
+			wrong = true;
+		}
+
+		lcd.print("*");
+	}
+
+	lcd.clear();
+
+	if (wrong) {
+		lcd.print("Incorrect!");
+		delay(2000);
+		return	false;
+	} else {
+		lcd.print("Pass!");
+		delay(2000);
+		return	true;
+	}
+
+	return false;
+}
+
+void WriteSysConfEEPROM(sys_conf str, int base) { // Запись и чтение выполнены великолепным программистом Виктором Охотниковым
+	char	*c;
+	int	 structSize = sizeof(sys_conf);
+
+	c = (char *) &str;
+
+	for(int i = 0; i < structSize; i++) {
+		EEPROM.write(i+base, *c);
+		c++;
+	}
+}
+
+void ReadSysConfEEPROM(sys_conf *str, int base) {
+	char	*c;
+	int	 structSize = sizeof(sys_conf);
+
+	c = (char *) str;
+
+	for(int i = 0; i < structSize; i++) {
+		*c = EEPROM.read(i+base);
+		c++;
+	}
+}
+
+void road_mode() {	// Режим спидометра
+	float	speed_old = 0.1;
+
+	lcd.clear();
+	lcd.print("km/h: ");
+
+	lcd.setCursor(0, 1);
+	lcd.print("km:");
+
+	lcd.setCursor(15, 1);
+	lcd.write(0);
+
+	#ifdef DEBUG
+	int	key_now;
+	#endif
+
+	while (system_mode == SPEED_MODE) {
+		if (speed_old > speed_now) {
+			lcd.setCursor(5, 0);
+			lcd.print("		");
+		}
+
+		if (speed_old != speed_now) {
+			lcd.setCursor(5, 0);
+			lcd.print(speed_now);
+			speed_old	= speed_now;
+		}
+
+		/*TIME START*/
+		lcd.setCursor(11, 0);
+
+		if (hour() < 10) {
+			lcd.print("0");
+		}
+
+		lcd.print(hour());
+		lcd.print(":");
+
+		lcd.setCursor(14, 0);
+
+		if (minute() < 10) {
+			lcd.print("0");
+		}
+
+		lcd.print(minute());
+		/*TIME END*/
+
+		lcd.setCursor(3, 1);
+		lcd.print(distance);
+
+		lcd.setCursor(12, 1);
+		if (bat_percent == 100) {
+			lcd.print("100");
+		} else if ((bat_percent > 100) && (bat_percent <= 10)){
+			lcd.print(" ");
+			lcd.print(bat_percent);
+		} else if (bat_percent > 10){
+			lcd.print("	");
+			lcd.print(bat_percent);
+		}
+
+		switch(key_pressed(false)) {
+			case BUT_OK:		system_mode	= MENU_MODE;
+								break;
+
+			case BUT_UP:		break;
+			case BUT_DOWN:		break;
+			case BUT_SIGNAL:	break;
+		}
+
+		#ifdef DEBUG
+		delay(500);
+		#endif
+	}
+
+	while ((analogRead(ACTION_BUTTON) > 5) && (sys_watch()));	// Ожидание отжатия кнопки
+}
+
+void calibration() {
+	byte	key_num = 0;
+
+	while (key_num != 3) {
+		while (analogRead(ACTION_BUTTON) > 5);
+		lcd.clear();
+
+		if (key_num == 0) {
+			lcd.print("Press OK key");
+			lcd.setCursor(0, 1);
+
+			while ((btc_config.button_ok = analog_to_byte(analogRead(ACTION_BUTTON))) < 2);
+
+			lcd.print(btc_config.button_ok);
+			key_num++;
+			continue;
+		}
+
+		if (key_num == 1) {
+			lcd.print("Press UP key");
+			lcd.setCursor(0, 1);
+
+			while ((btc_config.button_up = analog_to_byte(analogRead(ACTION_BUTTON))) < 2);
+
+			lcd.print(btc_config.button_up);
+			key_num++;
+			continue;
+		}
+
+		if (key_num == 2) {
+			lcd.print("Press DOWN key");
+			lcd.setCursor(0, 1);
+
+			while ((btc_config.button_down = analog_to_byte(analogRead(ACTION_BUTTON))) < 2);
+
+			lcd.print(btc_config.button_down);
+			key_num++;
+			continue;
+		}
+
+		if (key_num == 3) {
+			lcd.print("Press SIGNAL key");
+			lcd.setCursor(0, 1);
+
+			while ((btc_config.button_signal = analog_to_byte(analogRead(ACTION_BUTTON))) < 2);
+
+			lcd.print(btc_config.button_signal);
+			key_num++;
+		}
+
+		if (key_num == 4) {
+			lcd.print("Press SIGNAL+OK");
+			lcd.setCursor(0, 1);
+
+			btc_config.button_ok_signal	= 0;
+
+			while ((analog_to_byte(analogRead(ACTION_BUTTON)) > 2) || (btc_config.button_ok_signal == 0)) {
+				btc_config.button_ok_signal	= analog_to_byte(analogRead(ACTION_BUTTON));
+			}
+
+
+			lcd.print(btc_config.button_ok_signal);
+			key_num++;
+		}
+	}
+
+	while (analogRead(ACTION_BUTTON) > 5);
+	lcd.print("Key OK!");
+	delay(2000);
+}
+
+void self_test() {
+	byte	i;
+
+	lcd.clear();
+	lcd.print("Light sensor");
+
+	digitalWrite(HEADLIGHT, LOW);
+	digitalWrite(LOWER_LIGHT, LOW);
+	digitalWrite(RED_BACK_LIGHT, LOW);
+	registerWrite(0);
+
+	while (analogRead(ACTION_BUTTON) < 5) {
+		lcd.setCursor(0, 1);
+		lcd.print("    ");
+		lcd.setCursor(0, 1);
+		lcd.print(analogRead(LIGHT_SENSOR));
+		delay(500);
+	}
+
+	lcd.clear();
+	lcd.print("Key test");
+
+	while (analogRead(ACTION_BUTTON) > 5);
+
+	while (true) {
+		lcd.setCursor(0, 1);
+		lcd.print("    ");
+		lcd.setCursor(0, 1);
+		lcd.print(analogRead(ACTION_BUTTON));
+		delay(500);
+		if ((analogRead(ACTION_BUTTON) > (btc_config.button_ok - 5)) && (analogRead(ACTION_BUTTON) < (btc_config.button_ok + 5))) break;
+	}
+
+	lcd.clear();
+	lcd.print("Back light test");
+
+	while (analogRead(ACTION_BUTTON) > 5);
+
+	i	= 0;
+
+	while (true) {
+		lcd.setCursor(0, 1); lcd.print("   "); lcd.setCursor(0, 1); lcd.print(i);
+		registerWrite(i, HIGH);
+		i++;
+
+		if (i == 3) i	= 0;
+		delay(500);
+		if ((analogRead(ACTION_BUTTON) > (btc_config.button_ok - 5)) && (analogRead(ACTION_BUTTON) < (btc_config.button_ok + 5))) break;
+	}
+
+	registerWrite(0, LOW);
+
+	while (analogRead(ACTION_BUTTON) > 5);
+
+	lcd.clear();
+	lcd.print("PWM test");
+
+	i	= 0;
+
+	while (true) {
+		analogWrite(HEADLIGHT, i);
+		analogWrite(LOWER_LIGHT, i);
+		analogWrite(RED_BACK_LIGHT, i);
+		lcd.setCursor(0, 1); lcd.print("   "); lcd.setCursor(0, 1); lcd.print(i);
+		i++;
+
+		if (i == 255) i	= 0;
+		delay(5);
+		if ((analogRead(ACTION_BUTTON) > (btc_config.button_ok - 5)) && (analogRead(ACTION_BUTTON) < (btc_config.button_ok + 5))) break;
+	}
+
+	registerWrite(254);
+
+	lcd.clear();
+	lcd.print("Test end.");
+
+	while (analogRead(ACTION_BUTTON) > 5);
+}
+
+void engineering_menu() {
+	char en_menu[][15] = {
+		"Calibration",
+		"Self test",
+		"Continue work"
+	};
 }


Change pins for SoftwareSerial.

Change pins for SoftwareSerial.

--- main.ino
+++ main.ino
@@ -6,7 +6,7 @@
 static const int PM10_NORM=40;

 // RX, TX
-SoftwareSerial mySerial(9,8);
+SoftwareSerial mySerial(8,9);

 // SCLK, DIN, DC, CS, RST
 /* Adafruit_PCD8544 display = Adafruit_PCD8544(A5, A4, A3, A2, A1); */


[lmr] Synced receive code, still testing

--- arduino/lmremote/lmremote.ino
+++ arduino/lmremote/lmremote.ino
@@ -4,14 +4,13 @@

 // Enabling LMREMOTE_SERIAL also disables several power saving features
 #define LMREMOTE_SERIAL 38400
-#define RECEIVE_TEST 1

 // Base Idenfier for the RFM12B (0-63)
 // The transmitted ID is this ID plus the pin number
 const char _rfNodeBaseId = 0;
 // RFM12B band RF12_433MHZ, RF12_868MHZ, RF12_915MHZ
 const unsigned char _rfBand = RF12_915MHZ;
-// How long to sleep between probe measurments, in seconds
+// How many seconds to delay between measurements
 const unsigned char _sleepInterval = 2;
 // Analog pins to read. This is a bitfield, LSB is analog 0
 const unsigned char _enabledProbePins = 0x01;
@@ -53,20 +52,32 @@
   #define SLEEPMODE_ADC   SLEEP_MODE_ADC
 #endif

+#define RECV_CYCLE_TIME  1000    // expected receive cycle, millisecond
+#define MIN_RECV_WIN     8       // minimum window size, power of 2
+#define MAX_RECV_WIN     512     // maximum window size, power of 2
+
 static unsigned int _previousReads[RF_PINS_PER_SOURCE];
+static unsigned long _tempReadLast;
 static unsigned int _loopCnt;
 static unsigned char _sameCount;
 static unsigned char _isRecent = BYTE1_RECENT_BOOT;
 static unsigned char _isBattLow;
-static volatile unsigned char _adcBusy;
+
+static unsigned int _recvCycleAct;
+static unsigned int _recvWindow;
+static unsigned long _recvLast;
+static bool _recvSynced;
+
+static volatile bool _adcBusy;
+static volatile bool _watchdogWaiting;

 // The WDT is used solely to wake us from sleep
-ISR(WDT_vect) { wdt_disable(); }
-ISR(ADC_vect) { _adcBusy = 0; }
-
-static void packetReceived(unsigned char nodeId, unsigned int val)
-{
-#ifdef LMREMOTE_SERIAL
+ISR(WDT_vect) { _watchdogWaiting = false; }
+ISR(ADC_vect) { _adcBusy = false; }
+
+static bool packetReceived(unsigned char nodeId, unsigned int val)
+{
+#if LMREMOTE_SERIAL
   Serial.print(F("IN("));
   Serial.print(nodeId);
   Serial.print(F(")="));
@@ -75,11 +86,12 @@
 #endif

   if (nodeId != NODEID_MASTER)
-    return;
+    return false;
   // val contains requested fan speed percent
-}
-
-static void rf12_doWork(void)
+  return true;
+}
+
+static bool rf12_doWork(void)
 {
   if (rf12_recvDone() && rf12_crc == 0)
   {
@@ -87,14 +99,15 @@

     unsigned char nodeId = ((rf12_buf[0] & 0x0f) << 2) | (rf12_buf[1] >> 6);
     unsigned int val = (rf12_buf[1] & 0x0f) << 8 | rf12_buf[2];
-    packetReceived(nodeId, val);
+    return packetReceived(nodeId, val);
   }
   if (_pinLedRx != 0xff) digitalWrite(_pinLedRx, LOW);
+  return false;
 }

 static unsigned int analogReadSleep(unsigned char pin)
 {
-  _adcBusy = 1;
+  _adcBusy = true;
   ADMUX = (DEFAULT << 6) | pin;
   bitSet(ADCSRA, ADIE);
   set_sleep_mode(SLEEPMODE_ADC);
@@ -103,20 +116,10 @@
   return ADC;
 }

-static void sleep(uint8_t wdt_period, boolean include_adc)
+static void sleepPeriod(uint8_t wdt_period)
 {
   set_sleep_mode(SLEEP_MODE_PWR_DOWN);

-  // Disable ADC
-  if (include_adc)
-    ADCSRA &= ~bit(ADEN);
-
-  // TODO: Figure out what else I can safely disable
-  // Disable analog comparator to
-  // Internal Voltage Reference?
-  //   When turned on again, the user must allow the reference to start up before the output is used.
-  //   these should be disabled at all times, not just sleep
-
   // Set the watchdog to wake us up and turn on its interrupt
   wdt_enable(wdt_period);
   WDTCSR |= bit(WDIE);
@@ -131,24 +134,124 @@
   sleep_cpu();

   // Back from sleep
+  wdt_disable();
   sleep_disable();
-  if (include_adc)
-    ADCSRA |= bit(ADEN);
-}
-
-static void sleepSeconds(unsigned char secs)
-{
-#if RECEIVE_TEST
+}
+
+static void sleep(unsigned int msec)
+// Code copied from Sleepy::loseSomeSleep(), jeelib
+{
+  unsigned int msleft = msec;
+  while (msleft >= 16)
+  {
+    char wdp = 0; // wdp 0..9 corresponds to roughly 16..8192 ms
+    // calc wdp as log2(msleft/16), i.e. loop & inc while next value is ok
+    for (unsigned int m = msleft; m >= 32; m >>= 1)
+      if (++wdp >= 9)
+        break;
+    _watchdogWaiting = true;
+    sleepPeriod(wdp);
+    unsigned int halfms = 8 << wdp;
+    msleft -= halfms;
+    if (_watchdogWaiting)
+      continue;
+    msleft -= halfms;
+  }
+
+  // adjust the milli ticks, since we will have missed several
+#if defined(__AVR_ATtiny84__) || defined(__AVR_ATtiny85__) || defined (__AVR_ATtiny44__)
+    extern volatile unsigned long millis_timer_millis;
+    millis_timer_millis += msecs - msleft;
+#else
+    extern volatile unsigned long timer0_millis;
+    timer0_millis += msec - msleft;
+#endif
+}
+
+static void radioSleep(unsigned int ms)
+{
+  rf12_sleep(RF12_SLEEP);
+  sleep(ms);
+  rf12_sleep(RF12_WAKEUP);
+}
+
+static void resetEstimate(void)
+{
+#if _DEBUG
+  Serial.print(F("Resetting Estimate\n"));
+#endif
+  _recvCycleAct = RECV_CYCLE_TIME;
+  _recvWindow = MAX_RECV_WIN;
+  _recvSynced = false;
+
   unsigned long start = millis();
-  while (millis() - start < (secs * 1000U))
-    rf12_doWork();
-  ADCSRA |= bit(ADEN);
-#else
-  while (secs >= 8) { sleep(WDTO_8S, true); secs -=8; }
-  if (secs >= 4) { sleep(WDTO_4S, true); secs -= 4; }
-  if (secs >= 2) { sleep(WDTO_2S, true); secs -= 2; }
-  if (secs >= 1) { sleep(WDTO_1S, true); }
-#endif
+  while (!rf12_doWork())
+    if (millis() - start > RECV_CYCLE_TIME)
+      return;
+  _recvLast = millis();
+}
+
+static bool optimalSleep(void)
+// Code adapted from jeelib/examples/syncRecv optimalSleep()
+{
+  unsigned char lost = (millis() - _recvLast + _recvCycleAct / 2) / _recvCycleAct;
+  if (lost > 10)
+  {
+    resetEstimate();
+    return false;
+  }
+
+  // double the window every N packets lost
+  if (lost > 0 && lost % 2 == 0 && _recvWindow < MAX_RECV_WIN)
+    _recvWindow *= 2;
+
+  unsigned long predict = _recvLast + (lost + 1) * _recvCycleAct;
+  unsigned int sleep =  predict - millis() - _recvWindow;
+  radioSleep(sleep);
+
+  unsigned long recvTime;
+  unsigned long startTime = millis();
+  do {
+    recvTime = millis();
+    if (recvTime > predict + _recvWindow)
+    {
+#if _DEBUG
+      Serial.print(" f "); Serial.print(lost);
+      Serial.print(" s "); Serial.print(sleep);
+      Serial.print(" e "); Serial.print(_recvCycleAct);
+      Serial.print(" w "); Serial.print(_recvWindow);
+      Serial.print(" s "); Serial.print(startTime);
+      Serial.print(" p "); Serial.print(predict);
+      Serial.print(" r "); Serial.println(recvTime);
+      Serial.flush();
+#endif
+      return false;
+    }
+  } while (!rf12_doWork());
+
+  unsigned int newEst = (recvTime - _recvLast) / (lost + 1);
+  if (_recvSynced)
+    _recvCycleAct = (4 * _recvCycleAct + newEst + 3) / 5; // 5-fold smoothing
+  else
+    _recvCycleAct = newEst;
+  _recvLast = recvTime;
+
+#if _DEBUG
+  Serial.print(" n "); Serial.print(lost);
+  Serial.print(" e "); Serial.print(_recvCycleAct);
+  Serial.print(" E "); Serial.print(newEst);
+  Serial.print(" w "); Serial.print(_recvWindow);
+  Serial.print(" s "); Serial.print(startTime);
+  Serial.print(" p "); Serial.print(predict);
+  Serial.print(" r "); Serial.println(recvTime);
+#endif
+
+  if (_recvWindow > MIN_RECV_WIN)
+    _recvWindow /= 2;
+  else
+    _recvSynced = true;
+
+  return true;
 }

 static void updateBatteryLow(void)
@@ -200,7 +303,7 @@
   updateBatteryLow();
   // We're done with the ADC shut it down until the next wake cycle
   ADCSRA &= ~bit(ADEN);
-  if (_isRecent && (_loopCnt > (RECENT_EXPIRE_SECS/_sleepInterval)))
+  if (_isRecent && (millis() > RECENT_EXPIRE_SECS))
   {
     //Serial.print("No longer recent\n");
     _isRecent = 0;
@@ -211,18 +314,16 @@
   {
     if (PIN_DISABLED(pin))
       continue;
-    if (hasTransmitted) sleep(WDTO_15MS, false);
+    if (hasTransmitted) sleep(16);
     transmitTemp(pin);
     hasTransmitted = true;
   }

-#if RECEIVE_TEST == 0
   rf12_sleep(RF12_SLEEP);
-#endif
   if (_pinLedTx != 0xff)
   {
     digitalWrite(_pinLedTx, HIGH);
-    sleep(WDTO_15MS, false);
+    sleep(16);
     digitalWrite(_pinLedTx, LOW);
   }
 }
@@ -281,6 +382,8 @@
   Serial.print(" Checking temps: ");
 #endif

+  // Enable the ADC
+  ADCSRA |= bit(ADEN);
   enableAdcPullups();
   stabilizeAdc();
   for (unsigned char pin=0; pin < RF_PINS_PER_SOURCE; ++pin)
@@ -321,6 +424,10 @@
   }
   else
     ++_sameCount;
+  // Disable the ADC
+  ADCSRA &= ~bit(ADEN);
+
+  _tempReadLast = millis();
 }

 static void setupSupplyPins(void)
@@ -364,12 +471,18 @@

 void loop(void)
 {
-  checkTemps();
+  if (_loopCnt % 2 == 0)
+    checkTemps();
+
 #ifdef LMREMOTE_SERIAL
   Serial.flush(); delay(2);
 #endif
-  sleepSeconds(_sleepInterval);
+
+  if (_recvLast == 0)
+    resetEstimate();
+  else
+    optimalSleep();
   ++_loopCnt;
 }

-
+


Fix example DCCInterface_TurntableControl.ino sketch to work with library changes

--- examples/DCCInterface_TurntableControl/DCCInterface_TurntableControl.ino
+++ examples/DCCInterface_TurntableControl/DCCInterface_TurntableControl.ino
@@ -31,6 +31,9 @@
 // Uncomment the next line to enable Powering-Off the Stepper when its not running to reduce heating the motor and driver
 #define DISABLE_OUTPUTS_IDLE
 #endif
+
+// Uncomment the following line to enable Debug Print of DCC Messages
+//#define NOTIFY_DCC_MSG

 // By default the stepper motor will move the shortest distance to the desired position.
 // If you need the turntable to only move in the Positive/Increasing or Negative/Decreasing step numbers to better handle backlash in the mechanism
@@ -122,16 +125,11 @@
 uint8_t lastDirection = 0xFF;
 int     lastStep = 0;

-// This function is called whenever a normal DCC Turnout Packet is received
-void notifyDccAccTurnoutOutput( uint16_t Addr, uint8_t Direction, uint8_t OutputPower )
-{
-  Serial.print(F("notifyDccAccTurnoutOutput: "));
-  Serial.print(Addr,DEC) ;
-  Serial.print(',');
-  Serial.print(Direction,DEC) ;
-  Serial.print(',');
-  Serial.println(OutputPower, HEX) ;
-
+
+void processTurnoutCommand(uint16_t Addr, uint8_t Direction, uint8_t OutputPower)
+{
+  Serial.print(F("processTurnoutCommand: "));
+
   for (int i = 0; i < MAX_TURNOUT_POSITIONS ; i++)
   {
     if ((Addr == turnoutPositions[i].dccAddress) && ((Addr != lastAddr) || (Direction != lastDirection)) && OutputPower)
@@ -189,6 +187,22 @@
       break;
     }
   }
+}
+
+
+// This function is called from the Library whenever a normal DCC Turnout Packet is received
+void notifyDccAccTurnoutBoard (uint16_t BoardAddr, uint8_t OutputPair, uint8_t Direction, uint8_t OutputPower)
+{
+  uint16_t Addr = ((BoardAddr - 1) * 4) + OutputPair + 1;
+
+  Serial.print(F("notifyDccAccTurnoutBoard: "));
+  Serial.print(Addr,DEC) ;
+  Serial.print(',');
+  Serial.print(Direction,DEC) ;
+  Serial.print(',');
+  Serial.println(OutputPower, HEX) ;
+
+  processTurnoutCommand(Addr, Direction, OutputPower);
 };

 #ifdef DISABLE_OUTPUTS_IDLE
@@ -256,7 +270,7 @@
 #endif

   // Call the main DCC Init function to enable the DCC Receiver
-  Dcc.init( MAN_ID_DIY, 10, CV29_ACCESSORY_DECODER | CV29_OUTPUT_ADDRESS_MODE, 0 );
+  Dcc.init( MAN_ID_DIY, 10, CV29_ACCESSORY_DECODER, 0 );
 }

 void setup()
@@ -296,7 +310,7 @@
     setupDCCDecoder();

     // Fake a DCC Packet to cause the Turntable to move to Position 1
-    notifyDccAccTurnoutOutput(POSITION_01_DCC_ADDRESS, 1, 1);
+    processTurnoutCommand(POSITION_01_DCC_ADDRESS, 1, 1);
   }
 }

@@ -320,3 +334,16 @@
   }
 #endif
 }
+
+#ifdef  NOTIFY_DCC_MSG
+void notifyDccMsg( DCC_MSG * Msg)
+{
+  Serial.print("notifyDccMsg: ") ;
+  for(uint8_t i = 0; i < Msg->Size; i++)
+  {
+    Serial.print(Msg->Data[i], HEX);
+    Serial.write(' ');
+  }
+  Serial.println();
+}
+#endif


-Cleanup.

-Cleanup.


updates moving back to if statements to control movement

--- BitController/BitController.ino
+++ BitController/BitController.ino
@@ -28,10 +28,10 @@
 const uint8_t east = A2;
 const uint8_t south = A3;

-int nVal = 0;
-int wVal = 0;
-int eVal = 0;
-int sVal = 0;
+double nVal = 0;
+double wVal = 0;
+double eVal = 0;
+double sVal = 0;

 int n = 0;
 int w = 1;
@@ -40,12 +40,12 @@

 const int arr_size = 4;

-int sensorVals[arr_size] = {0};
-
-int n_base = 0;
-int w_base = 0;
-int e_base = 0;
-int s_base = 0;
+double sensorVals[arr_size] = {0};
+
+double n_base = 0;
+double w_base = 0;
+double e_base = 0;
+double s_base = 0;

 //motor control
@@ -125,27 +125,39 @@
   Serial.println();
 }

-
 void readSensors()
 {
-  int north_intensity = analogRead(north);
-  int west_intensity = analogRead(west);
-  int east_intensity = analogRead(east);
+  int north_temp = 0;
+  int west_temp = 0;
+  int east_temp = 0;
+  //int north_temp = 0;
+  for (int i = 0; i < 10; i++)
+  {
+    north_temp += analogRead(north);
+    west_temp += analogRead(west);
+    east_temp += analogRead(east);
+    delay(50);
+  }
+
+  nVal = north_temp/10.0 - n_base;
+  wVal = west_temp/10.0 - w_base;
+  eVal = east_temp/10.0 - e_base;
+
+//  int north_intensity = analogRead(north);
+//  int west_intensity = analogRead(west);
+//  int east_intensity = analogRead(east);
   //int south_intensity = analogRead(south);

-
-  nVal = north_intensity - n_base;
-  wVal = west_intensity - w_base;
-  eVal = east_intensity - e_base;
+//  nVal = north_intensity - n_base;
+//  wVal = west_intensity - w_base;
+//  eVal = east_intensity - e_base;
   //sVal = south_intensity - s_base;
-

   //sensorVals[0] = {nVal, eVal, sVal, wVal};
   sensorVals[n] = nVal;
   sensorVals[w] = wVal;
   sensorVals[e] = eVal;
-  //sensorVals[s] = sVal;
-
+  //sensorVals[s] = sVal;
 }

@@ -201,8 +213,9 @@
 {
   readSensors();
   printSensors();
-  sensorVals[s] = 20;
-  drive(sensorVals[n], sensorVals[s], sensorVals[e], sensorVals[w]);
+  //sensorVals[s] = 300;
+  determineDirection();
+  //drive(sensorVals[n], sensorVals[s], sensorVals[e], sensorVals[w]);

   BT.println();
   BT.println();
@@ -213,7 +226,7 @@
   //determineDirection();
   //drive(sensorVals[n], sensorVals[s], sensorVals[e], sensorVals[w]);
   //lcd.println();
-  delay(1500);
+  //delay(1500);
 }

@@ -290,90 +303,156 @@
   //check to see which direction has highest value
   //check to see which direction is second
   //check to see which direction is third
-
-  if ((sensorVals[n]*.6) > sensorVals[w] && (sensorVals[n]*.6) > sensorVals[e])
+  if(sensorVals[n] > 80 || sensorVals[w] > 80 || sensorVals[e] > 80)
+  {
+  if ((sensorVals[n]*.7) > sensorVals[w] || (sensorVals[n]*.7) > sensorVals[e])
   {
     if (abs(sensorVals[w]-sensorVals[e]) < 50)
     {
+      analogWrite(l1_motor, 200);
+      analogWrite(l2_motor, 0);
+      analogWrite(r1_motor, 200);
+      analogWrite(r2_motor, 0);
       //lcd.println("head north");
+      Serial.println("head north");
+      BT.println("head north");
     }
     else if (sensorVals[w]*1.2 >= sensorVals[e]*1.2)
     {
+      analogWrite(l1_motor, 50);
+      analogWrite(l2_motor, 0);
+      analogWrite(r1_motor, 200);
+      analogWrite(r2_motor, 0);
       //lcd.println("head north-west");
+      Serial.println("head north-west");
+      BT.println("head north-west");
     }
     else if (sensorVals[e]*1.2 >= sensorVals[w]*1.2)
     {
+      analogWrite(l1_motor, 200);
+      analogWrite(l2_motor, 0);
+      analogWrite(r1_motor, 50);
+      analogWrite(r2_motor, 0);
       //lcd.println("head north-east");
+      Serial.println("head north-east");
+      BT.println("head north-east");
     }
     else
     {
       //lcd.println("no direction or continue moving along last direction");
+      Serial.println("no direction or continue moving along last direction");
+      BT.println("no direction or continue moving along last direction");
       //some error
     }
   }
-  else if ((sensorVals[e]*.6) > sensorVals[n] && (sensorVals[e]*.6) > sensorVals[s])
-  {
-    if (abs(sensorVals[n]-sensorVals[s]) < 50)
-    {
-      //lcd.println("head east");
-    }
-    else if (sensorVals[n]*1.2 >= sensorVals[s]*1.2)
-    {
-      //lcd.println("head east-north-east");
-    }
-    else if (sensorVals[s]*1.2 >= sensorVals[n]*1.2)
-    {
-      //lcd.println("head east-south-east");
-    }
-    else
-    {
-      //lcd.println("no direction or continue moving along last direction");
-      //some error
-    }
-  }
-  else if ((sensorVals[w]*.6) > sensorVals[n] && (sensorVals[w]*.6) > sensorVals[s])
-  {
-    if (abs(sensorVals[n]-sensorVals[s]) < 50)
-    {
-     // lcd.println("head west");
-    }
-    else if (sensorVals[n]*1.2 >= sensorVals[s]*1.2)
-    {
-      //lcd.println("head west-north-west");
-    }
-    else if (sensorVals[s]*1.2 >= sensorVals[n]*1.2)
-    {
-      //lcd.println("head west-south-west");
-    }
-    else
-    {
-      //lcd.println("no direction or continue moving along last direction");
-      //some error
-    }
-  }
-  else if ((sensorVals[s]*.6) > sensorVals[w] && (sensorVals[s]*.6) > sensorVals[e])
-  {
-    if (abs(sensorVals[w]-sensorVals[e]) < 50)
-    {
-      //lcd.println("head south");
-    }
-    else if (sensorVals[w]*1.2 >= sensorVals[e]*1.2)
-    {
-      //lcd.println("head south-west");
-    }
-    else if (sensorVals[e]*1.2 >= sensorVals[w]*1.2)
-    {
-      //lcd.println("head south-east");
-    }
-    else
-    {
-      //lcd.println("no direction or continue moving along last direction");
-      //some error
-    }
-  }
+  //else if ((sensorVals[e]*.6) > sensorVals[n] && (sensorVals[e]*.6) > sensorVals[s])
+  else if ((sensorVals[e]*.65) > sensorVals[n] && sensorVals[e]*.9 > sensorVals[w])
+  //else if ((sensorVals[e]*.65) > sensorVals[n] && sensorVals[e] > 100)
+  {
+      analogWrite(l1_motor, 200);
+      analogWrite(l2_motor, 0);
+      analogWrite(r1_motor, 0);
+      analogWrite(r2_motor, 200);
+    Serial.println("head east");
+    BT.println("head east");
+//    if (abs(sensorVals[n]-sensorVals[s]) < 50)
+//    {
+//      //lcd.println("head east");
+//      Serial.println("head east");
+//      BT.println("head east");
+//    }
+//    else if (sensorVals[n]*1.2 >= sensorVals[s]*1.2)
+//    {
+//      //lcd.println("head east-north-east");
+//      Serial.println("head east-north-east");
+//      BT.println("head east-north-east");
+//    }
+//    else if (sensorVals[s]*1.2 >= sensorVals[n]*1.2)
+//    {
+//      //lcd.println("head east-south-east");
+//      Serial.println("head east-south-east");
+//      BT.println("head east-south-east");
+//    }
+//    else
+//    {
+//      //lcd.println("no direction or continue moving along last direction");
+//      Serial.println("no direction or continue moving along last direction");
+//      BT.println("no direction or continue moving along last direction");
+//      //some error
+//    }
+  }
+  //else if ((sensorVals[w]*.6) > sensorVals[n] && (sensorVals[w]*.6) > sensorVals[s])
+  else if ((sensorVals[w]*.65) > sensorVals[n] && sensorVals[w]*.9 > sensorVals[e])
+  //else if ((sensorVals[w]*.65) > sensorVals[n]  && sensorVals[w > 100)
+  {
+      analogWrite(l1_motor, 0);
+      analogWrite(l2_motor, 200);
+      analogWrite(r1_motor, 200);
+      analogWrite(r2_motor, 0);
+     Serial.println("head west");
+     BT.println("head west");
+//    if (abs(sensorVals[n]-sensorVals[s]) < 50)
+//    {
+//     // lcd.println("head west");
+//     Serial.println("head west");
+//     BT.println("head west");
+//    }
+//    else if (sensorVals[n]*1.2 >= sensorVals[s]*1.2)
+//    {
+//      //lcd.println("head west-north-west");
+//      Serial.println("head west-north-west");
+//      BT.println("head west-north-west");
+//    }
+//    else if (sensorVals[s]*1.2 >= sensorVals[n]*1.2)
+//    {
+//      //lcd.println("head west-south-west");
+//      Serial.println("head west-south-west");
+//      BT.println("head west-south-west");
+//    }
+//    else
+//    {
+//      //lcd.println("no direction or continue moving along last direction");
+//      Serial.println("no direction or continue moving along last direction");
+//      BT.println("no direction or continue moving along last direction");
+//      //some error
+//    }
+  }
+//  else if ((sensorVals[s]*.6) > sensorVals[w] && (sensorVals[s]*.6) > sensorVals[e])
+//  {
+//    if (abs(sensorVals[w]-sensorVals[e]) < 50)
+//    {
+//      //lcd.println("head south");
+//    }
+//    else if (sensorVals[w]*1.2 >= sensorVals[e]*1.2)
+//    {
+//      //lcd.println("head south-west");
+//    }
+//    else if (sensorVals[e]*1.2 >= sensorVals[w]*1.2)
+//    {
+//      //lcd.println("head south-east");
+//    }
+//    else
+//    {
+//      //lcd.println("no direction or continue moving along last direction");
+//      //some error
+//    }
+//  }
   else
   {
     //lcd.println("got no where");
+    Serial.println("got no where");
+    BT.println("got no where");
+  }
+  }
+  else
+  {
+      analogWrite(l1_motor, 0);
+      analogWrite(l2_motor, 0);
+      analogWrite(r1_motor, 0);
+      analogWrite(r2_motor, 0);
+     Serial.println("no signal");
+     BT.println("no signal");
+
   }
 }

@@ -404,6 +483,12 @@

   if (val_ns - val_ew > 0) //Left motors
   {
+//    for (int i = 0; i < val_ns - val_ew; i++)
+//    {
+//      analogWrite(l1_motor, i);
+//      delay(1);
+//
+//    }
     analogWrite(l1_motor, val_ns - val_ew); //(l1 high & l2 low, motors go forward)
     analogWrite(l2_motor, 0);
   }


semaphor example change

semaphor example change

--- examples/semaphore/semaphore.ino
+++ examples/semaphore/semaphore.ino
@@ -26,13 +26,20 @@
 #define NUM_EVENTS     20   //supported events
 #define NUM_EVENT_VARS 0    //no need for supported event variables
 #define DEVICE_NUM     1    //one device number
+#define MODULE_ID      55   //module id
+#define MANUFACTURER_ID 165 //manufacturer id
+#define MIN_CODE       0    //min code version
+#define MAX_CODE       1    //max code version
+
+#define CANPORT        53   //attached mcp2551 pin
+
+#define PUSH_BUTTON1    6    //std merg push button

 //semaphore leds
 #define GREEN 10              //green led pin
 #define YELLOW 11             //yellow led pin
 #define RED 12                //red led pin
 #define TRANSITION_TIME  20   //time in milli to keep the yellow light on
-#define

 MergCBUS cbus=MergCBUS(NUM_NODE_VARS,NUM_EVENTS,NUM_EVENT_VARS,DEVICE_NUM);

@@ -49,11 +56,11 @@

   //Configuration data for the node
-  cbus.getNodeId()->setNodeName("MODTESTE",8);  //node name
-  cbus.getNodeId()->setModuleId(55);            //module number
-  cbus.getNodeId()->setManufacturerId(0xA5);    //merg code
-  cbus.getNodeId()->setMinCodeVersion(1);       //Version 1
-  cbus.getNodeId()->setMaxCodeVersion(0);
+  cbus.getNodeId()->setNodeName("SEMAPHOR",8);         //node name
+  cbus.getNodeId()->setModuleId(MODULE_ID);            //module number
+  cbus.getNodeId()->setManufacturerId(MANUFACTURER_ID);//merg code
+  cbus.getNodeId()->setMinCodeVersion(MIN_CODE);       //Version 1
+  cbus.getNodeId()->setMaxCodeVersion(MAX_CODE);
   cbus.getNodeId()->setProducerNode(false);
   cbus.getNodeId()->setConsumerNode(true);
   cbus.setStdNN(999); //standard node number
@@ -69,7 +76,7 @@
   cbus.setLeds(GREEN_LED,YELLOW_LED);//set the led ports
   cbus.setPushButton(PUSH_BUTTON);//set the push button ports
   cbus.setUserHandlerFunction(&myUserFunc);//function that implements the node logic
-  cbus.initCanBus(53,CAN_125KBPS,10,200);  //initiate the transport layer
+  cbus.initCanBus(CANPORT);  //initiate the transport layer

   Serial.println("Setup finished");
 }


Create timers for each plug and transmit measurements when required.

--- JnGeneral/JnGeneral.ino
+++ JnGeneral/JnGeneral.ino
@@ -27,7 +27,7 @@

 // The scheduler makes it easy to perform various tasks at various times:

-enum { TASK_ANNOUNCE=0, TASK_MEASURE, TASK_REPORT, TASK_END };
+enum { TASK_ANNOUNCE=0, TASK_REPORT, TASK_MEASURE0, TASK_END=TASK_MEASURE0+MAX_PLUGS };
 static word schedbuf[TASK_END];
 Scheduler scheduler (schedbuf, TASK_END);

@@ -39,6 +39,17 @@
 // Lame floating point format, only powers of ten = mant*10^exp
 // 4 bits mantissa (0..15), 4 bits exponent (-8..7)
 #define SCALE(mant,exp) (((exp&0xF) << 4) | (mant&0xF))
+
+static int scale_as_int(byte scale)
+{
+    int n = scale & 0xF;
+    int e = scale >> 4;
+    while(e > 0) {
+        n *= 10;
+        e--;
+    }
+    return n;
+}

 enum { UNIT_HUMIDITY, UNIT_TEMP, UNIT_VOLT, UNIT_OHM, UNIT_SCALAR, UNIT_TESLA, UNIT_PASCAL };

@@ -607,8 +618,6 @@

     if(record) {
         bufferMeasurements(plug, measurements);
-        if(scheduler.idle(TASK_REPORT))
-            scheduler.timer(TASK_REPORT, 1);
     }
     return 0;
 }
@@ -619,11 +628,14 @@
     Serial.print("Doing measurements:\r\n");
     for(byte n=0; n<count; n++) {
         for(byte i=0; i<numPlugs; i++) {
-            measurePlug(plugs[i], n == 0);
+            // If doing one measurement, send the results
+            measurePlug(plugs[i], count == 1);
         }
         if( (n+1) < count )
             Sleepy::loseSomeTime(1000);
     }
+    if(count == 1 && scheduler.idle(TASK_REPORT))
+        scheduler.timer(TASK_REPORT, 1);
 }

 static void prompt()
@@ -640,6 +652,8 @@

     for(byte i=0; i<numPlugs; i++) {
         init_measure(plugs[i]);
+        // Measure only after a minute, so the user can interrupt
+        scheduler.timer(TASK_MEASURE0+i, 600);
     }
     showHelp();
     showConfig();
@@ -648,6 +662,8 @@

     rf12_config(0);         // Setup RF
     rf12_sleep(RF12_SLEEP); // and power down
+
+    databuffer[databufferpos++] = 'D';    // init output buffer

     scheduler.timer(TASK_ANNOUNCE, 0);    // start the announcements
 }
@@ -672,31 +688,35 @@
     } else {
         event = scheduler.pollWaiting();
     }
-    switch (event) {
-        case TASK_ANNOUNCE:
-            // Repeat every minute for the first five minutes, then once per hour
-            scheduler.timer(TASK_ANNOUNCE, millis() < 300000 ? 600 : 36000);
-
-            sendAnnouncement();
-            break;
-
-#if 0
-        case MEASURE:
-            // reschedule these measurements periodically
-            scheduler.timer(MEASURE, MEASURE_PERIOD);
-
-            doMeasure();
-
-            // every so often, a report needs to be sent out
-            if (++reportCount >= REPORT_EVERY) {
-                reportCount = 0;
-                scheduler.timer(REPORT, 0);
-            }
-            break;
-
-        case REPORT:
-            doReport();
-            break;
-#endif
-    }
-}
+    if(event == TASK_ANNOUNCE) {
+        // Repeat every minute for the first five minutes, then once per hour
+        scheduler.timer(TASK_ANNOUNCE, millis() < 300000 ? 600 : 36000);
+
+        sendAnnouncement();
+    } else if(event == TASK_REPORT) {
+        // Transmit any buffered measurements
+        Serial.print("\r\n=> ");
+        for(byte j=0; j<databufferpos; j++) {
+            printInt(databuffer[j]);
+            Serial.print(",");
+        }
+        Serial.print("\r\n");
+        serialFlush();
+
+        rf12_sleep(RF12_WAKEUP);
+        rf12_sendNow(0, databuffer, databufferpos);
+        rf12_sendWait(RADIO_SYNC_MODE);
+        rf12_sleep(RF12_SLEEP);
+
+        databufferpos = 1;  // Don't overwrite header
+    } else if(event >= TASK_MEASURE0 && event <= TASK_MEASURE0+MAX_PLUGS) {
+        // Take the measurement for the given plug and then schedule a report
+        Plug &plug = plugs[event-TASK_MEASURE0];
+
+        scheduler.timer(event, scale_as_int(plug.period));
+
+        measurePlug(plug, 1);
+        if(scheduler.idle(TASK_REPORT))
+            scheduler.timer(TASK_REPORT, 1);
+    }
+}


TODO-970: tidyup

TODO-970: tidyup

--- Arduino/V0p2_Main/V0p2_Main.ino
+++ Arduino/V0p2_Main/V0p2_Main.ino
@@ -512,38 +512,15 @@
   const unsigned long usEnd = micros();
   // Nominal loop time should be 2s x 1MHz clock, ie 2,000,000 if CPU running all the time.
   // Should generally be <2000 (<0.1%) for leaf, <20000 (<1%) for hub.
+  // Example output.
+//us apparent: 4544
+//us apparent: 25280
+//us apparent: 9280
   const unsigned long usApparentTaken = usEnd - usStart;
 #if 1 && defined(DEBUG)
   DEBUG_SERIAL_PRINT_FLASHSTRING("us apparent: ");
   DEBUG_SERIAL_PRINT(usApparentTaken);
   DEBUG_SERIAL_PRINTLN();
-// Leaf sample 2014/11/22...
-//us apparent: 4544
-//us apparent: 25280
-//us apparent: 9280
-//us apparent: 68416
-//=F0%@19C7;IC2E0;V3230;X0;R81;T8 1 W255 0 F255 0 W255 0 F255 0;S12 12 16 e;o34
-//
-//>
-//us apparent: 339136
-//us apparent: 1600
-//us apparent: 2112
-//us apparent: 2880
-//us apparent: 3008
-//us apparent: 1408
-//us apparent: 1344
-//Bare stats TX
-//us apparent: 74368
-//{"@":"c2e0","T|C16":311,"H|%":81,"L":238,"B|cV":323}
-//us apparent: 119232
-//us apparent: 1408
-//...
-//us apparent: 3008
-//us apparent: 1344
-//us apparent: 3264
-//us apparent: 1408
-//us apparent: 3776
-//us apparent: 2816
-#endif
-#endif
-  }
+#endif
+#endif
+  }


Update of code to specify email were the images taken will sent

--- AutomatedHomeSecuritySystem.ino
+++ AutomatedHomeSecuritySystem.ino
@@ -1,61 +1,63 @@
 #define CUSTOM_SETTINGS
-#define INCLUDE_BUZZER_SHIELD
-#define INCLUDE_CAMERA_SHIELD
-#define INCLUDE_EMAIL_SHIELD
+#define INCLUDE_BUZZER_SHIELD  // Calling of library classes for
+#define INCLUDE_CAMERA_SHIELD //the functions needed for the
+#define INCLUDE_EMAIL_SHIELD // virtualization of shields on the 1sheeld android app
+
 #define trigPin 6
 #define echoPin 5
 #include <OneSheeld.h>
-
 //declaration of varibles for leds
 int led = 13;
 int led2 = 12;
 int led3 = 11;
-
 int duration, distance;//declare distance and duration as integers;
-

 void setup()
 {
-  Serial.begin(9600);
+  // put your setup code here, to run once:
+  //serial monitor and pin setup.
+  Serial.begin(115200);
   OneSheeld.begin();
   pinMode(trigPin, OUTPUT);
   pinMode(echoPin, INPUT);
-   pinMode(led, OUTPUT);
+  pinMode(led, OUTPUT);
   pinMode(led2, OUTPUT);
   pinMode(led3, OUTPUT);
+  //Scheduler.startLoop(loop2);
+
 }

 void loop()
 {

   ultrasonic();
-  if(distance > 0 && distance <= 30.0 )
+  if(distance > 0 && distance <= 30.0 )// distance can be increased to desired distance
   {
     Serial.print("Trigger at :");
     Serial.println(distance);
-    digitalWrite(led, HIGH);
-    delay(100);               // wait for a second
-   digitalWrite(led, LOW);
-   delay(100);
-
-  digitalWrite(led2, HIGH);
-  delay(100);               // wait for a second
-   digitalWrite(led2, LOW);
-   delay(100);
-  digitalWrite(led3, HIGH);
-  delay(100);               // wait for a second
-   digitalWrite(led3, LOW);
-   delay(100);
+
+
     Camera.setFlash(ON);
     Camera.rearCapture();
     delay(5000);
-    Camera.setFlash(OFF);
+    Camera.setFlash(OFF);
     //recipient, subject, message
-    Email.attachLastPicture("onughachimobi@gmail.com","Presence detected","Intruder Alert");
-   Buzzer.buzzOn();
-    delay(10000);
+    Email.attachLastPicture("gets83hit@photos.flickr.com","Presence detected","Intruder Alert");
+
+    Buzzer.buzzOn();
+
+      for (int i=1; i<=10; i++)
+      {
+        blinktimer();
+       delay(1000);
+      }
+
     Buzzer.buzzOff();
     delay(30000);
+    //turns off leds,
+    //ultrasonic sensor and buzzer for 30seconds.
+    //After this, the ultrasonic sensor is turned on and
+    //stays on until it is triggered again

   }

@@ -65,11 +67,31 @@
 {
   digitalWrite(trigPin, LOW);
   delayMicroseconds(2);
-  digitalWrite(trigPin,HIGH);// trigin sends out signal
+  digitalWrite(trigPin,HIGH);// send out signal
   delayMicroseconds(10);
   digitalWrite(trigPin, LOW);// then goes low

   duration = pulseIn(echoPin, HIGH);
   distance=(duration/2)/29.1; //  the 29.1 is used to convert the distance to cm, the value varies for other units.
   Serial.println(distance);
+}
+
+
+void blinktimer()//Method to make led blink when ultasonic sensor is triggered
+{
+    digitalWrite(led, HIGH);//blink
+    delay(100);               // wait for a second
+    digitalWrite(led, LOW);
+    delay(100);
+
+    digitalWrite(led2, HIGH);//blink
+    delay(100);               // wait for a second
+    digitalWrite(led2, LOW);
+    delay(100);
+
+    digitalWrite(led3, HIGH); //blink
+    delay(100);               // wait for a second
+    digitalWrite(led3, LOW);
+    delay(100);
+
 }


updates

updates

--- BitController/BitController.ino
+++ BitController/BitController.ino
@@ -112,6 +112,17 @@
   BT.print(e_base);
   BT.println();
   BT.println();
+
+  Serial.print("north: ");
+  Serial.print(n_base);
+  Serial.print("\t");
+  Serial.print("west: ");
+  Serial.print(w_base);
+  Serial.print("\t");
+  Serial.print("east: ");
+  Serial.print(e_base);
+  Serial.println();
+  Serial.println();
 }

@@ -147,9 +158,20 @@
   BT.print(wVal);
   BT.print("\t");
   BT.print("east: ");
-  BT.print(eVal);
-  BT.println();
-  BT.println();
+  BT.println(eVal);
+//  BT.println();
+//  BT.println();
+
+  Serial.print("north: ");
+  Serial.print(nVal);
+  Serial.print("\t");
+  Serial.print("west: ");
+  Serial.print(wVal);
+  Serial.print("\t");
+  Serial.print("east: ");
+  Serial.println(eVal);
+//  Serial.println();
+//  Serial.println();

 //  lcd.clear();
 //  lcd.setCursor(0,0);
@@ -179,8 +201,13 @@
 {
   readSensors();
   printSensors();
-  sensorVals[s] = 1;
+  sensorVals[s] = 20;
   drive(sensorVals[n], sensorVals[s], sensorVals[e], sensorVals[w]);
+
+  BT.println();
+  BT.println();
+  Serial.println();
+  Serial.println();
   //BT.println("hello world");
   //dmove();
   //determineDirection();
@@ -201,6 +228,7 @@
     //go north
     //lcd.print("go north");
     BT.print("go north");
+    Serial.print("go north");
     analogWrite(l1_motor, 255);
     analogWrite(l2_motor, 0);
     analogWrite(r1_motor, 255);
@@ -212,6 +240,7 @@
     //go east
     //lcd.print("go east");
     BT.print("go east");
+    Serial.print("go east");
     analogWrite(l1_motor, 255);
     analogWrite(l2_motor, 0);
     analogWrite(r1_motor, 0);
@@ -222,6 +251,7 @@
     //go north east
     //lcd.print("go north-east");
     BT.print("go north-east");
+    Serial.print("go north-east");
     analogWrite(l1_motor, 255);
     analogWrite(l2_motor, 0);
     analogWrite(r1_motor, 55);
@@ -233,20 +263,24 @@
     //continue along previous path
     //lcd.print("don't know");
     BT.print("don't know");
+    Serial.print("don't know");
   }
   }
   else
   {
     //lcd.print("no signal");
     BT.print("no signal");
+    Serial.print("no signal");
     analogWrite(l1_motor, 0);
     analogWrite(l2_motor, 0);
     analogWrite(r1_motor, 0);
     analogWrite(r2_motor, 0);
   }

-  BT.println();
-  BT.println();
+//  BT.println();
+//  BT.println();
+//  Serial.println();
+//  Serial.println();
 }

@@ -352,9 +386,21 @@
   int val2 = 0;
   int val3 = 0;

-  val_ns = map(log10(nx/sx), -log10(600), log10(600), -127, 127); //S at -127, N at 127
-  val_ew = map(log10(ex/sx), -log10(600), log10(600), -127, 127); //W at -127, E at 127
+  val_ns = map(log(nx/sx), -log(30), log(30), -127, 127); //S at -127, N at 127
+  val_ew = map(log(ex/wx), -log(30), log(30), -127, 127); //W at -127, E at 127
   //The summed/subtracted range of val_ns with val_ew is +/-254
+
+  Serial.print("val_ns: ");
+  Serial.print(val_ns);
+  Serial.print("\t");
+  Serial.print("val_ew: ");
+  Serial.println(val_ew);
+
+  BT.print("val_ns: ");
+  BT.print(val_ns);
+  BT.print("\t");
+  BT.print("val_ew: ");
+  BT.println(val_ew);

   if (val_ns - val_ew > 0) //Left motors
   {


Adjust targets to default 30S Nissan Leaf cells

Adjust targets to adopt 30 Series (15 cans) Nissan Leaf cells @4.10v

--- BridgeConnect_SigIn_EnPower.ino
+++ BridgeConnect_SigIn_EnPower.ino
@@ -1,293 +1,293 @@
-// -------------------------------------------------------------
-//  bridgeconnect firmware for SigIn monitor to transmit to EnPower charger
-//  version 1.0  22-July-2016 initial release
-// -------------------------------------------------------------
-// targets defined for charger based on operating modes
-
-const uint16_t HIPOWER_MAX_VOLT = 530; // 0.1v/bit  typically 73.8v
-const uint16_t HIPOWER_MAX_AMP  = 150; // 0.1A/bit  typically 40.0A
-const uint16_t LOPOWER_MAX_VOLT = 530; // 0.1v/bit  typically 73.8v
-const uint16_t LOPOWER_MAX_AMP  =  18; // 0.1A/bit  typically  1.0A
-
-// -------------------------------------------------------------
-// variable related to canbus port 2
-#include <Metro.h>
-#include <SPI.h>
-#include "mcp_can.h"
-
-#define TRACE_TX_MSG    (false)
-#define TRACE_RX_MSG    (true)
-#define TRACE_CALC_TGTS (true)
-
-const int  SPI_CS_PIN = 28;  // pin assignement for CAN2
-MCP_CAN    CAN2(SPI_CS_PIN); // Set CAN2 SPI CS pin
-
-unsigned long canRxId;       // RX can identifier
-byte          canRxLen;      // RX packet length
-byte          canRxBuf[8];   // RX data buffer
-byte          canTxBuf[8];   // TX data buffer
-
-Metro canRxTimer = Metro(10);  // check charger status every 10 milliseconds
-Metro canTxTimer = Metro(500); // send charger targets every 500 miliseconds
-
-// -------------------------------------------------------------
-
-#include     "SigStateMgmt.h"
-#define      TRACE_SIGIN_MODE (true)
-#define      PULSE_INPUT_PIN  (25)
-SigStateMgmt SigIn;
-EnumSigState SigInState;
-Metro        sigInTimer = Metro(1000); // refresh sigin monitor every 1000 miliseconds
-
-// -------------------------------------------------------------
-// -------------------------------------------------------------
-// -------------------------------------------------------------
-
-static uint8_t hex[17] = "0123456789abcdef";
-
-typedef union
-{
-  uint16_t val;
-  uint8_t dat[2];
-} UINT16UNION_t;
-
-void hexDump(uint8_t dumpLen, uint8_t *bytePtr)
-{
-  uint8_t working;
-  while ( dumpLen-- ) {
-    working = *bytePtr++;
-    Serial.write( hex[ working >> 4 ] );
-    Serial.write( hex[ working & 15 ] );
-  }
-  Serial.write('\r');
-  Serial.write('\n');
-}
-
-// -------------------------------------------------------------
-
-void setup(void)
-{
-  Serial.begin(115200);
-  delay(1000); // wait for serial port ready
-
-  Serial.println("BridgeConnect SigIn-EnPower controller v1.0");
-
-  while (CAN_OK != CAN2.begin(CAN_500KBPS))
-  {
-    Serial.println("CAN2 init fail");
-    delay(100);
-  }
-  Serial.println("CAN2 init ok!");
-
-  SigIn.setup(PULSE_INPUT_PIN);
-  delay(1000);
-  Serial.println("SigIn monitor enabled.");
-
-  canRxTimer.reset();
-  canTxTimer.reset();
-  sigInTimer.reset();
-}
-
-// -------------------------------------------------------------
-
-void loop(void)
-{
-  if ( canRxTimer.check() )
-  {
-    while (CAN_OK == CAN2.readMsgBufID(&canRxId, &canRxLen, canRxBuf))
-    {
-      CanbusMgmt_EnPower_FilterReadMsg();
-    }
-  }
-
-  if ( canTxTimer.check() )
-  {
-    CanbusMgmt_EnPower_Transmit_Targets();
-  }
-
-  SigIn.loop();
-  if ( sigInTimer.check() )
-  {
-    RefreshSigInState();
-  }
-}
-
-// -------------------------------------------------------------
-
-void CanbusMgmt_EnPower_FilterReadMsg()
-{
-  switch (canRxId)
-  {
-    case 0x18EB2440:
-      CanbusMgmt_EnPower_Parse_ActualStatus();
-      break;
-    default:
-      // if nothing else matches, do the default
-      // default is optional
-      // hexDump( sizeof(canRxBuf), (uint8_t *)&canRxBuf );
-      break;
-  }
-}
-
-void CanbusMgmt_EnPower_Parse_ActualStatus()
-{
-  UINT16UNION_t volt;
-  UINT16UNION_t amp;
-
-  volt.dat[0] = canRxBuf[2];
-  volt.dat[1] = canRxBuf[3];
-  amp.dat[0] = canRxBuf[4];
-  amp.dat[1] = canRxBuf[5];
-
-#if TRACE_RX_MSG
-  Serial.print(F("RX Actuals ***                    "));
-  Serial.print(" volt=");
-  Serial.print(volt.val);
-  Serial.print(" amp=");
-  Serial.print(amp.val);
-  Serial.print(" run=");
-  Serial.print(canRxBuf[1]);
-  Serial.print(" status=");
-  Serial.print(canRxBuf[0]);
-  Serial.print("\n\r");
-  hexDump( sizeof(canRxBuf), (uint8_t *)&canRxBuf );
-#endif
-}
-
-// -------------------------------------------------------------
-
-void CanbusMgmt_EnPower_Transmit_Targets()
-{
-  uint16_t MaxVolt = 510;  // 0.1v/bit
-  uint16_t MaxAmp =   10;  // 0.1A/bit
-  bool ChargeDisable = false;
-
-#if TRACE_CALC_TGTS
-
-  switch (SigInState)
-  {
-    case SIG_STATE_OFF:
-      MaxVolt = 0;
-      MaxAmp  = 0;
-      ChargeDisable = true;
-      break;
-
-    case SIG_STATE_COMPLETED_CHARGE:
-      MaxVolt = 0;
-      MaxAmp  = 0;
-      ChargeDisable = true;
-      break;
-
-    case SIG_STATE_LOW_CURRENT:
-      MaxVolt = LOPOWER_MAX_VOLT;
-      MaxAmp  = LOPOWER_MAX_AMP;
-      ChargeDisable = false;
-      break;
-
-    case SIG_STATE_HIGH_CURRENT:
-      MaxVolt = HIPOWER_MAX_VOLT;
-      MaxAmp  = HIPOWER_MAX_AMP;
-      ChargeDisable = false;
-      break;
-
-    case SIG_STATE_DISABLE:
-      MaxVolt = 0;
-      MaxAmp  = 0;
-      ChargeDisable = true;
-      break;
-
-    case SIG_STATE_ENABLE:
-      MaxVolt = HIPOWER_MAX_VOLT;
-      MaxAmp  = HIPOWER_MAX_AMP;
-      ChargeDisable = false;
-      break;
-
-    case SIG_STATE_UNDEFINED:
-      MaxVolt = 0;
-      MaxAmp  = 0;
-      ChargeDisable = true;
-      break;
-  }
-
-#endif
-
-  CanbusMgmt_EnPower_Write_Targets(MaxVolt, MaxAmp, ChargeDisable);
-
-#if TRACE_TX_MSG
-  Serial.print(F("TX Targets                    "));
-  Serial.print(" MaxVolt=");
-  Serial.print(MaxVolt);
-  Serial.print(" MaxAmp=");
-  Serial.print(MaxAmp);
-  Serial.print(" Disable=");
-  Serial.print(ChargeDisable);
-  Serial.print("\n\r");
-  hexDump( sizeof(canTxBuf), (uint8_t *)&canTxBuf );
-#endif
-}
-
-void CanbusMgmt_EnPower_Write_Targets(uint16_t MaxVolt, uint16_t MaxAmp,  bool ChargeDisable)
-{
-  // 0.1A/bit 3200 offset (hence -320.0A to +400.0A) hence negative is charging
-  uint16_t AmpOffset = 3200 - MaxAmp;
-
-  canTxBuf[0] = (ChargeDisable) ? 0 : 252;
-  canTxBuf[1] = lowByte(MaxVolt);
-  canTxBuf[2] = highByte(MaxVolt);
-  canTxBuf[3] = lowByte(AmpOffset);
-  canTxBuf[4] = highByte(AmpOffset);
-  canTxBuf[5] = (ChargeDisable) ? 0x03 : 0x05;  // Green LED status on Charger not lite for 0.5s
-  canTxBuf[6] = 0xFF;  // Reserved
-  canTxBuf[7] = 0xFF;  // Reserved
-
-  // send data: id = 0x01, extended, data len = 8, testData
-  CAN2.sendMsgBuf(0x18E54024, 1, 8, canTxBuf);
-}
-
-// -------------------------------------------------------------
-
-void RefreshSigInState()
-{
-  SigInState = SigIn.ReadSigState();
-
-#if TRACE_SIGIN_MODE
-  Serial.print("Pulse Freqency (Hz): ");
-  Serial.print(SigIn.ReadPulseFreqHz());
-  Serial.print("   ");
-
-  switch (SigInState)
-  {
-    case SIG_STATE_OFF:
-      Serial.println("SIG_STATE_OFF");
-      break;
-
-    case SIG_STATE_COMPLETED_CHARGE:
-      Serial.println("SIG_STATE_COMPLETED_CHARGE");
-      break;
-
-    case SIG_STATE_LOW_CURRENT:
-      Serial.println("SIG_STATE_LOW_CURRENT");
-      break;
-
-    case SIG_STATE_HIGH_CURRENT:
-      Serial.println("SIG_STATE_HIGH_CURRENT");
-      break;
-
-    case SIG_STATE_DISABLE:
-      Serial.println("SIG_STATE_DISABLE");
-      break;
-
-    case SIG_STATE_ENABLE:
-      Serial.println("SIG_STATE_ENABLE");
-      break;
-
-    case SIG_STATE_UNDEFINED:
-      Serial.println("SIG_STATE_UNDEFINED");
-      break;
-  }
-#endif
-}
-
-// -------------------------------------------------------------
-
-
+// -------------------------------------------------------------
+//  bridgeconnect firmware for SigIn monitor to transmit to EnPower charger
+//  version 1.0  22-July-2016 initial release
+// -------------------------------------------------------------
+// targets defined for charger based on operating modes
+
+const uint16_t HIPOWER_MAX_VOLT = 1230; // 0.1v/bit  typically 123.0v (30S @ 4.10v)
+const uint16_t HIPOWER_MAX_AMP  =  250; // 0.1A/bit  typically  25.0A
+const uint16_t LOPOWER_MAX_VOLT = 1230; // 0.1v/bit  typically 123.0v
+const uint16_t LOPOWER_MAX_AMP  =   10; // 0.1A/bit  typically   1.0A
+
+// -------------------------------------------------------------
+// variable related to canbus port 2
+#include <Metro.h>
+#include <SPI.h>
+#include "mcp_can.h"
+
+#define TRACE_TX_MSG    (false)
+#define TRACE_RX_MSG    (true)
+#define TRACE_CALC_TGTS (true)
+
+const int  SPI_CS_PIN = 28;  // pin assignement for CAN2
+MCP_CAN    CAN2(SPI_CS_PIN); // Set CAN2 SPI CS pin
+
+unsigned long canRxId;       // RX can identifier
+byte          canRxLen;      // RX packet length
+byte          canRxBuf[8];   // RX data buffer
+byte          canTxBuf[8];   // TX data buffer
+
+Metro canRxTimer = Metro(10);  // check charger status every 10 milliseconds
+Metro canTxTimer = Metro(500); // send charger targets every 500 miliseconds
+
+// -------------------------------------------------------------
+
+#include     "SigStateMgmt.h"
+#define      TRACE_SIGIN_MODE (true)
+#define      PULSE_INPUT_PIN  (25)
+SigStateMgmt SigIn;
+EnumSigState SigInState;
+Metro        sigInTimer = Metro(1000); // refresh sigin monitor every 1000 miliseconds
+
+// -------------------------------------------------------------
+// -------------------------------------------------------------
+// -------------------------------------------------------------
+
+static uint8_t hex[17] = "0123456789abcdef";
+
+typedef union
+{
+  uint16_t val;
+  uint8_t dat[2];
+} UINT16UNION_t;
+
+void hexDump(uint8_t dumpLen, uint8_t *bytePtr)
+{
+  uint8_t working;
+  while ( dumpLen-- ) {
+    working = *bytePtr++;
+    Serial.write( hex[ working >> 4 ] );
+    Serial.write( hex[ working & 15 ] );
+  }
+  Serial.write('\r');
+  Serial.write('\n');
+}
+
+// -------------------------------------------------------------
+
+void setup(void)
+{
+  Serial.begin(115200);
+  delay(1000); // wait for serial port ready
+
+  Serial.println("BridgeConnect SigIn-EnPower controller v1.0");
+
+  while (CAN_OK != CAN2.begin(CAN_500KBPS))
+  {
+    Serial.println("CAN2 init fail");
+    delay(100);
+  }
+  Serial.println("CAN2 init ok!");
+
+  SigIn.setup(PULSE_INPUT_PIN);
+  delay(1000);
+  Serial.println("SigIn monitor enabled.");
+
+  canRxTimer.reset();
+  canTxTimer.reset();
+  sigInTimer.reset();
+}
+
+// -------------------------------------------------------------
+
+void loop(void)
+{
+  if ( canRxTimer.check() )
+  {
+    while (CAN_OK == CAN2.readMsgBufID(&canRxId, &canRxLen, canRxBuf))
+    {
+      CanbusMgmt_EnPower_FilterReadMsg();
+    }
+  }
+
+  if ( canTxTimer.check() )
+  {
+    CanbusMgmt_EnPower_Transmit_Targets();
+  }
+
+  SigIn.loop();
+  if ( sigInTimer.check() )
+  {
+    RefreshSigInState();
+  }
+}
+
+// -------------------------------------------------------------
+
+void CanbusMgmt_EnPower_FilterReadMsg()
+{
+  switch (canRxId)
+  {
+    case 0x18EB2440:
+      CanbusMgmt_EnPower_Parse_ActualStatus();
+      break;
+    default:
+      // if nothing else matches, do the default
+      // default is optional
+      // hexDump( sizeof(canRxBuf), (uint8_t *)&canRxBuf );
+      break;
+  }
+}
+
+void CanbusMgmt_EnPower_Parse_ActualStatus()
+{
+  UINT16UNION_t volt;
+  UINT16UNION_t amp;
+
+  volt.dat[0] = canRxBuf[2];
+  volt.dat[1] = canRxBuf[3];
+  amp.dat[0] = canRxBuf[4];
+  amp.dat[1] = canRxBuf[5];
+
+#if TRACE_RX_MSG
+  Serial.print(F("RX Actuals ***                    "));
+  Serial.print(" volt=");
+  Serial.print(volt.val);
+  Serial.print(" amp=");
+  Serial.print(amp.val);
+  Serial.print(" run=");
+  Serial.print(canRxBuf[1]);
+  Serial.print(" status=");
+  Serial.print(canRxBuf[0]);
+  Serial.print("\n\r");
+  hexDump( sizeof(canRxBuf), (uint8_t *)&canRxBuf );
+#endif
+}
+
+// -------------------------------------------------------------
+
+void CanbusMgmt_EnPower_Transmit_Targets()
+{
+  uint16_t MaxVolt = 510;  // 0.1v/bit
+  uint16_t MaxAmp =   10;  // 0.1A/bit
+  bool ChargeDisable = false;
+
+#if TRACE_CALC_TGTS
+
+  switch (SigInState)
+  {
+    case SIG_STATE_OFF:
+      MaxVolt = 0;
+      MaxAmp  = 0;
+      ChargeDisable = true;
+      break;
+
+    case SIG_STATE_COMPLETED_CHARGE:
+      MaxVolt = 0;
+      MaxAmp  = 0;
+      ChargeDisable = true;
+      break;
+
+    case SIG_STATE_LOW_CURRENT:
+      MaxVolt = LOPOWER_MAX_VOLT;
+      MaxAmp  = LOPOWER_MAX_AMP;
+      ChargeDisable = false;
+      break;
+
+    case SIG_STATE_HIGH_CURRENT:
+      MaxVolt = HIPOWER_MAX_VOLT;
+      MaxAmp  = HIPOWER_MAX_AMP;
+      ChargeDisable = false;
+      break;
+
+    case SIG_STATE_DISABLE:
+      MaxVolt = 0;
+      MaxAmp  = 0;
+      ChargeDisable = true;
+      break;
+
+    case SIG_STATE_ENABLE:
+      MaxVolt = HIPOWER_MAX_VOLT;
+      MaxAmp  = HIPOWER_MAX_AMP;
+      ChargeDisable = false;
+      break;
+
+    case SIG_STATE_UNDEFINED:
+      MaxVolt = 0;
+      MaxAmp  = 0;
+      ChargeDisable = true;
+      break;
+  }
+
+#endif
+
+  CanbusMgmt_EnPower_Write_Targets(MaxVolt, MaxAmp, ChargeDisable);
+
+#if TRACE_TX_MSG
+  Serial.print(F("TX Targets                    "));
+  Serial.print(" MaxVolt=");
+  Serial.print(MaxVolt);
+  Serial.print(" MaxAmp=");
+  Serial.print(MaxAmp);
+  Serial.print(" Disable=");
+  Serial.print(ChargeDisable);
+  Serial.print("\n\r");
+  hexDump( sizeof(canTxBuf), (uint8_t *)&canTxBuf );
+#endif
+}
+
+void CanbusMgmt_EnPower_Write_Targets(uint16_t MaxVolt, uint16_t MaxAmp,  bool ChargeDisable)
+{
+  // 0.1A/bit 3200 offset (hence -320.0A to +400.0A) hence negative is charging
+  uint16_t AmpOffset = 3200 - MaxAmp;
+
+  canTxBuf[0] = (ChargeDisable) ? 0 : 252;
+  canTxBuf[1] = lowByte(MaxVolt);
+  canTxBuf[2] = highByte(MaxVolt);
+  canTxBuf[3] = lowByte(AmpOffset);
+  canTxBuf[4] = highByte(AmpOffset);
+  canTxBuf[5] = (ChargeDisable) ? 0x03 : 0x05;  // Green LED status on Charger not lite for 0.5s
+  canTxBuf[6] = 0xFF;  // Reserved
+  canTxBuf[7] = 0xFF;  // Reserved
+
+  // send data: id = 0x01, extended, data len = 8, testData
+  CAN2.sendMsgBuf(0x18E54024, 1, 8, canTxBuf);
+}
+
+// -------------------------------------------------------------
+
+void RefreshSigInState()
+{
+  SigInState = SigIn.ReadSigState();
+
+#if TRACE_SIGIN_MODE
+  Serial.print("Pulse Freqency (Hz): ");
+  Serial.print(SigIn.ReadPulseFreqHz());
+  Serial.print("   ");
+
+  switch (SigInState)
+  {
+    case SIG_STATE_OFF:
+      Serial.println("SIG_STATE_OFF");
+      break;
+
+    case SIG_STATE_COMPLETED_CHARGE:
+      Serial.println("SIG_STATE_COMPLETED_CHARGE");
+      break;
+
+    case SIG_STATE_LOW_CURRENT:
+      Serial.println("SIG_STATE_LOW_CURRENT");
+      break;
+
+    case SIG_STATE_HIGH_CURRENT:
+      Serial.println("SIG_STATE_HIGH_CURRENT");
+      break;
+
+    case SIG_STATE_DISABLE:
+      Serial.println("SIG_STATE_DISABLE");
+      break;
+
+    case SIG_STATE_ENABLE:
+      Serial.println("SIG_STATE_ENABLE");
+      break;
+
+    case SIG_STATE_UNDEFINED:
+      Serial.println("SIG_STATE_UNDEFINED");
+      break;
+  }
+#endif
+}
+
+// -------------------------------------------------------------
+
+


Changed commit to indicate  Processing 3 The example is now tested and works with Processing 3. Comment was missing.

--- build/shared/examples/10.StarterKit_BasicKit/p14_TweakTheArduinoLogo/p14_TweakTheArduinoLogo.ino
+++ build/shared/examples/10.StarterKit_BasicKit/p14_TweakTheArduinoLogo/p14_TweakTheArduinoLogo.ino
@@ -9,8 +9,8 @@
  10 kilohm potentiometer

  Software required :
- Processing http://processing.org
- Active internet connection
+ Processing  (3.0 or newer) http://processing.org
+ Active internet connection

  Created 18 September 2012
  by Scott Fitzgerald


Use Redbearlab pin by default

Use Redbearlab pin by default

--- libraries/BLE/examples/ble_uart_project_with_dfu_template/ble_uart_project_with_dfu_template.ino
+++ libraries/BLE/examples/ble_uart_project_with_dfu_template/ble_uart_project_with_dfu_template.ino
@@ -157,8 +157,8 @@
    * The Active pin is optional and can be marked UNUSED
    */
   aci_state.aci_pins.board_name = BOARD_DEFAULT; //See board.h for details REDBEARLAB_SHIELD_V1_1 or BOARD_DEFAULT
-  aci_state.aci_pins.reqn_pin   = SS; //SS for Nordic board, 9 for REDBEARLAB_SHIELD_V1_1
-  aci_state.aci_pins.rdyn_pin   = 3; //3 for Nordic board, 8 for REDBEARLAB_SHIELD_V1_1
+  aci_state.aci_pins.reqn_pin   = 9; //SS for Nordic board, 9 for REDBEARLAB_SHIELD_V1_1
+  aci_state.aci_pins.rdyn_pin   = 8; //3 for Nordic board, 8 for REDBEARLAB_SHIELD_V1_1
   aci_state.aci_pins.mosi_pin   = MOSI;
   aci_state.aci_pins.miso_pin   = MISO;
   aci_state.aci_pins.sck_pin    = SCK;


cleaning up for alpha release

cleaning up for alpha release

--- display/display.ino
+++ display/display.ino
@@ -46,7 +46,7 @@

 // Create ECG trace
-ECGReadout ecg = ECGReadout(10,50,tft.height() - BOXSIZE, 100, 15 , 0, &tft);
+ECGReadout ecg = ECGReadout(10,50,tft.height() - BOXSIZE, 100, 14 , 0, &tft);

 /*
  * draw_submenu() - draws color box submenu on left of screen


Serial needs to run much faster to be able to keep up with the speed of the rotary encoder output

--- oven.ino
+++ oven.ino
@@ -20,7 +20,7 @@
 int lastDisplayValue = 0;

 // Pin numbers for the RGB LEB
-const int ledRedPin = 8;
+const int ledRedPin = 6;
 const int ledGreenPin = 9;
 const int ledBluePin = 10;

@@ -31,11 +31,12 @@
 // Will be used with sprintf to create strings
 char tempString[10];

+// Piezo buzzer pin number
 int buzzerPin = 7;

-void setup()
-{
-  Serial.begin(9600);
+
+void setup() {
+  Serial.begin(115200);

   // Attach interrupts for rotary encoder
   re_setup();
@@ -155,8 +156,6 @@
     // divided by the note type.
     //e.g. quarter note = 1000 / 4, eighth note = 1000/8, etc.
     int noteDuration = 1800/noteDurations[thisNote];
-    Serial.println(melody[thisNote]);
-    Serial.println(noteDuration);
     tone(buzzerPin, melody[thisNote], noteDuration);

     // Change LED color


The oven now has a clock

The oven now has a clock

--- oven.ino
+++ oven.ino
@@ -8,12 +8,13 @@
 // Pin number the push button is connected to
 const int buttonPin = 13;

-// The last state the button was in
+// The push button states
 int buttonState = 0;
 int lastButtonState = 0;
-
-// This MOD the number of states determines the state we are in
-int buttonPressCounter = 0;
+boolean wasLongPress = false;
+
+// This is the mode the program is currently in
+int mode = 0;

 // Number to display on the LED S7S
 int displayValue = 0;
@@ -33,6 +34,23 @@

 // Piezo buzzer pin number
 int buzzerPin = 7;
+
+// Place to store current time
+unsigned long now;
+long offset = 0;
+
+// The time (in ms) when the button was pressed down
+unsigned long buttonDownTime;
+
+// Amount of time (in ms) to hold the button down to set the clock
+const int buttonSetClockDuration = 5000;  // 10 seconds
+
+
+const int MODE_CLOCK = 0;
+const int MODE_SET_COOK_TIME = 1;
+const int MODE_COOK = 2;
+const int MODE_SET_CLOCK = 3;
+

 void setup() {
@@ -49,15 +67,14 @@
   pinMode(ledRedPin, OUTPUT);
   pinMode(ledGreenPin, OUTPUT);
   pinMode(ledBluePin, OUTPUT);
-
-  Wire.begin();  // Initialize hardware I2C pins
-
-  // Clear the display, and then turn on all segments and decimals
-  s7s.clearDisplay();  // Clears display, resets cursor
-
-  // Custom function to send four bytes via I2C
-  //  The I2C.write function only allows sending of a single
-  //  byte at a time.
+
+  // Initialize hardware I2C pins for S7S
+  Wire.begin();
+
+  // Clear display, reset cursor
+  s7s.clearDisplay();
+
+  // Welcome
   s7s.sendString("-HI-");
   delay(2000);

@@ -65,33 +82,109 @@
   s7s.clearDisplay();
 }

-void loop()
-{
-  if (hasButtonBeenPushed()) {
-    Serial.println("Button Pushed");
-    buttonPressCounter++;
-    Serial.println(buttonPressCounter);
-  }
-
-  switch (buttonPressCounter % 3) {
-    case 0:
-      setColor(0, 255, 0);
-      adjustTime();
-      break;
-    case 1:
+
+void loop() {
+  doButtonCheck();
+
+  switch (mode) {
+    case MODE_CLOCK:
+      displayClock();
+      break;
+    case MODE_SET_COOK_TIME:
+      adjustCountdownTimer();
+      break;
+    case MODE_COOK:
       cooking();
       break;
-    case 2:
-      setColor(0, 0, 0);
-      s7s.clearDisplay();
-      displayValue = 0;
-      re_resetPulses();
+    case MODE_SET_CLOCK:
+      setClock();
       break;
   }
 }

-void adjustTime() {
+void doButtonCheck() {
+  // Read the state of the button
+  buttonState = digitalRead(buttonPin);
+  if (buttonState == LOW) {
+    if (lastButtonState == HIGH) {
+      Serial.println("Button Pushed");
+      switchMode();
+    }
+  } else {
+    if (lastButtonState == LOW) {
+      // Record time button was pushed
+      buttonDownTime = millis();
+    }
+
+    // Check for long press
+    if (millis() - buttonDownTime >= buttonSetClockDuration) {
+        Serial.println("Button pressed for 10 seconds");
+        wasLongPress = true;
+
+        // Set time setup goes here
+        setColor(0, 128, 255);
+        re_resetPulses();
+    }
+  }
+
+  // Save the previous state for the next loop
+  lastButtonState = buttonState;
+}
+
+
+void switchMode() {
+  if (wasLongPress) {
+    mode = MODE_SET_CLOCK;
+    wasLongPress = false;
+
+  } else {
+    // Normal mode switch
+    mode++;
+    mode = mode % 3;
+    Serial.print("Now in mode: ");
+    Serial.println(mode);
+  }
+}
+
+
+void displayClock() {
+  setColor(0, 0, 0);
+
+  now = millis() + offset + 86400000;
+  int seconds = (now / 1000) % 60;
+  int minutes = (now / 1000 / 60) % 60;
+  int hours = (now / 1000 / 60 / 60) % 12;
+
+  if (hours == 0) {
+    hours = 12;
+  }
+
+  sprintf(tempString, "%02d%02d", hours, minutes);
+  s7s.sendString(tempString);
+
+  if (seconds % 2 == 0) {
+    s7s.setDecimals(0b00010000);
+  } else {
+    s7s.setDecimals(0b00000000);
+  }
+}
+
+
+void setClock() {
+  setColor(0, 0, 255);
+
+  long pulses = (long) re_getPulses();
+  offset = (pulses / 4) * 1000 * 60;
+
+  displayClock();
+  s7s.setDecimals(0b00010000);
+}
+
+
+void adjustCountdownTimer() {
+  setColor(0, 255, 0);
+
   int pulses = re_getPulses();
   if (pulses < 0) {
     re_resetPulses();
@@ -100,6 +193,7 @@
   updateDisplay();
 }

+
 void cooking() {
   setColor(255, 0, 0);

@@ -112,14 +206,20 @@
     for (int i = 0; i < 5; i++) {
       tone(buzzerPin, NOTE_C1, 50);
       delay(50);
-      tone(buzzerPin, NOTE_D1, 50);
+      tone(buzzerPin, NOTE_C2, 50);
       delay(50);
     }
-  }
-}
+    noTone(buzzerPin);
+  }
+}
+

 void soupsReady() {
-  buttonPressCounter = 2;
+  // Switch to clock mode after song and dance
+  mode = MODE_CLOCK;
+
+  displayValue = 0;
+  re_resetPulses();

   // notes in the melody:
   int melody[] = {
@@ -131,7 +231,7 @@

   int colors[][3] = {
     {255, 255, 0},
-    {255, 255, 128},
+    {255, 255, 255}, // was 128 Blue (pin 10)
     {255, 255, 0},
     {255, 128, 0},
     {255, 0, 0},
@@ -180,23 +280,6 @@
   s7s.sendString(tempString);
 }

-/* Interrupt emulation. Detect when the button was pushed once and only once
- * while it is held down
- */
-boolean hasButtonBeenPushed() {
-  boolean hasButtonBeenPushed = false;
-
-  // Read the state of the button
-  buttonState = digitalRead(buttonPin);
-  if (buttonState == LOW) {
-    if (lastButtonState == HIGH) {
-      hasButtonBeenPushed = true;
-    }
-  }
-  lastButtonState = buttonState;
-
-  return hasButtonBeenPushed;
-}

 // Sets the color of the RGB LEB
@@ -207,3 +290,4 @@
   analogWrite(ledBluePin, 255 - blue);
 }

+


Fixed tone() in FSKModem example for ESP32 and Arduino Due

--- examples/FSKModem/FSKModem.ino
+++ examples/FSKModem/FSKModem.ino
@@ -152,13 +152,17 @@

   // using the direct mode, it is possible to transmit
   // FM notes with Arduino tone() function
-  // transmit FM note at 1000 Hz for 1 second
+
+  // tone() function is not available on ESP32 and Arduino Due
+  #if !defined(ESP32) && !defined(_VARIANT_ARDUINO_DUE_X_)
+  // transmit FM tone at 1000 Hz for 1 second
   // (DIO2 is connected to Arduino pin 4)
   tone(4, 1000);
   delay(1000);
   // transmit FM note at 500 Hz for 1 second
   tone(4, 500);
   delay(1000);
+  #endif

   // NOTE: you will not be able to send or receive packets
   // while direct mode is active! to deactivate it, call method


Sensor readings below a low threshold now ignored (as they seem to be spurious); now reports time to Serial3 regardless of whether or not it's in debug mode (to allow checking of the time on "release" version); and other minor tweaks before deployment

--- PassingPersonCounter.ino
+++ PassingPersonCounter.ino
@@ -29,11 +29,10 @@
 #define GPRS_PASSWORD  "" // replace with your GPRS password

 #define DEBUG 0
-#if DEBUG
+
 // The Mega-Hera200 doesn't expose Serial to the expansion connector
 // but Serial3 is on PJ0 and PJ1
 #define LOG_SERIAL_PORT Serial3
-#endif

 // How long each reading set should span (IN MINUTES!)
 const unsigned long kReadingInterval =15UL;
@@ -181,6 +180,9 @@
     }
     // Record when we took these readings
     time_t readingsTime = now();
+    batteryReadings[readingIdx].setTime(readingsTime);
+    chargingReadings[readingIdx].setTime(readingsTime);
+    sensorReadings[readingIdx].setTime(readingsTime);
 #if DEBUG
     LOG_SERIAL_PORT.println("Readings...");
     LOG_SERIAL_PORT.print("Time: ");
@@ -191,10 +193,8 @@
     LOG_SERIAL_PORT.println(chargingReadings[readingIdx].getInt());
     LOG_SERIAL_PORT.print("Movement: ");
     LOG_SERIAL_PORT.println(sensorReadings[readingIdx].getInt());
-#endif
-    batteryReadings[readingIdx].setTime(readingsTime);
-    chargingReadings[readingIdx].setTime(readingsTime);
-    sensorReadings[readingIdx].setTime(readingsTime);
+    LOG_SERIAL_PORT.println(feed);
+#endif
   }

   digitalWrite(kReportingLED, LOW);
@@ -244,7 +244,6 @@
     asm volatile ("  jmp 0");
   }

-  // The PIR sensor is active low
   if (digitalRead(kPIRSensorPin))
   {
     digitalWrite(kActivityDetectedLED, LOW);
@@ -255,16 +254,20 @@
     digitalWrite(kActivityDetectedLED, HIGH);
     // Find out how long we've been active, and use that to guide
     // how many people we think have passed
-    movementCount++;
-    if (millis()-movementStart < 10*60*1000UL)
-    {
-      movementCount += (millis()-movementStart)/kPassingTime;
-    }
-    else
-    {
-      // it's over 10 minutes, reckon it's someone loitering
-      // Probably at least two people then :-)
+    // But really short readings will be the sensor lying to us
+    if (millis()-movementStart > 3300)
+    {
       movementCount++;
+      if (millis()-movementStart < 10*60*1000UL)
+      {
+        movementCount += (millis()-movementStart)/kPassingTime;
+      }
+      else
+      {
+        // it's over 10 minutes, reckon it's someone loitering
+        // Probably at least two people then :-)
+        movementCount++;
+      }
     }
   }
 }
@@ -290,11 +293,13 @@
   {
     // The modem is reporting a time from the 2000s, which means
     // it's not the right time
+#if !DEBUG
+    LOG_SERIAL_PORT.begin(9600);
+#endif

     // Try to set it from the network
     if (!modem.setTimeFromNetwork(1*60*1000UL))
     {
-#if DEBUG
       LOG_SERIAL_PORT.println("Didn't get the time signal from the network");
       // Give the user a window to set it via the serial monitor
       LOG_SERIAL_PORT.println("Enter the time (in seconds since Jan 1 1970):");
@@ -307,16 +312,18 @@
         // We've been given a time, so let's use it
         modem.setTime(timeToString(now()));
       }
-#endif
     }
   }
   // Set the Time library time from the modem
   String modemTime = modem.getTime();
-#if DEBUG
   LOG_SERIAL_PORT.print("The time is ");
   LOG_SERIAL_PORT.println(modemTime);
-#endif
   setTimeFromModem(modemTime);
+  LOG_SERIAL_PORT.print("The internal time is ");
+  LOG_SERIAL_PORT.println(now());
+#if !DEBUG
+  LOG_SERIAL_PORT.end();
+#endif
 }

 String timeToString(time_t aTime)


Add back hack to get Bridge sensor working again

--- Arduino/libraries/UA_Sensors/examples/BridgeSensorGSM/BridgeSensorGSM.ino
+++ Arduino/libraries/UA_Sensors/examples/BridgeSensorGSM/BridgeSensorGSM.ino
@@ -9,7 +9,7 @@
   - Need to test if this version works on test sensor

   Created 14 6 2014
-  Modified 30 6 2014
+  Modified 1 7 2014
 */

 #include <LowPower.h>
@@ -98,6 +98,12 @@
   }

+  // HACK: Turn on GSM MOSFET on wake up each time. Somehow
+  //       fixes bug where RocketScream resets.
+  digitalWrite(MOSFET_GSM_PIN, HIGH);
+  delay(1000);
+
+
   // 2. Turn on thermistor.
   // ----------------------
   digitalWrite(THERM_PIN, HIGH);
@@ -222,13 +228,6 @@
       textMessage += String(DATA_DELIM) + String(minutesElapsed) + " " + String(sensorReadings[i].distance) + " " + String(sensorReadings[i].temperature);
     }

-
-    // 19. Turn on GSM Shied.
-    // ---------------------
-
-    //Turn on GSM MOSFET.
-    digitalWrite(MOSFET_GSM_PIN, HIGH);
-    delay(1000);

     // GSM baud rate. Start communication link with GSM shield.
     Serial.begin(19200);
@@ -267,9 +266,9 @@
       //                   Battery will die quickly if power cannot be turned off.
       //                   Send SOS SMS?
     }
-
-    // Turn off GSM MOSFET.
-    digitalWrite(MOSFET_GSM_PIN, LOW);
-    delay(1000);
-  }
+  }
+
+  // Turn off GSM MOSFET.
+  digitalWrite(MOSFET_GSM_PIN, LOW);
+  delay(1000);
 }


fix bug in timer usage

fix bug in timer usage

--- pokken/pokken.ino
+++ pokken/pokken.ino
@@ -25,7 +25,7 @@
   if (msTicked == 0)
     return;

-  msTicked = 1;
+  msTicked = 0;

   uint16_t btns = snes_read();


Full (2D) support for G28

Full (2D) support for G28

--- src/miscr.ino
+++ src/miscr.ino
@@ -269,12 +269,7 @@
 }

 /*
- * This function does not yet have any GCode parsing functionality,
- * it is currently only used for testing...
- *
- * Thanks to the blog post at:
- * https://www.marginallyclever.com/2013/08/how-to-build-an-2-axis-arduino-cnc-gcode-interpreter/
- * for helping me writing this function!
+ * Provides G-Code parsing functionality
  */
 bool parseGCode(String in) {
   int gindex = getIndex('G', in);
@@ -296,10 +291,19 @@

     return true;
   } else if(gindex == 28) {
-    if(globalPos.x != 0)
+    int xindex = in.indexOf("X");
+    int yindex = in.indexOf("Y");
+
+    if(xindex == -1 && yindex == -1) {
+      if(globalPos.x != 0)
+        sX.testSpin(globalPos.x - (globalPos.x * 2));
+      if(globalPos.y != 0)
+        sY.testSpin(globalPos.y - (globalPos.y * 2));
+    } else if(xindex != -1 && globalPos.x != 0) {
       sX.testSpin(globalPos.x - (globalPos.x * 2));
-    if(globalPos.y != 0)
+    } else if(yindex != -1 && globalPos.y != 0) {
       sY.testSpin(globalPos.y - (globalPos.y * 2));
+    }

     return true;
   }


Update repeating_pattern.ino

Update repeating_pattern.ino

renamed some variables

--- repeating_pattern.ino
+++ repeating_pattern.ino
@@ -8,6 +8,7 @@
 //
 // Marc Miller, Nov 2015
 //              May 2020 - replaced all delays with EVERY_N
+//              June 2021 - renamed some variables
 //***************************************************************

 #include "FastLED.h"
@@ -47,24 +48,24 @@
   }

   EVERY_N_MILLISECONDS(500) {
-    static uint8_t offset;
-    static uint8_t shift;
+    static uint8_t hueOffset;
+    static uint8_t hueShift;

-    //hue = ((255 / repeatEvery) * offset) + shift;  // Change the hue for each pixel set.
-    hue = (20 * offset) + shift;  // Change the hue for each pixel set.
+    //hue = ((255 / repeatEvery) * hueOffset) + hueShift;  // Change the hue for each pixel set.
+    hue = (20 * hueOffset) + hueShift;  // Change the hue for each pixel set.

     for (uint16_t x = 0; x < numberOfRepeats + 1; x++) {
       static uint16_t i;
-      i = (repeatEvery * (x - 1)) + repeatEvery + offset;  // The pixel number to draw
+      i = (repeatEvery * (x - 1)) + repeatEvery + hueOffset;  // The pixel number to draw
       if (i < NUM_LEDS) {  // Only draw pixel numbers within NUM_LEDS
         leds[i] = CHSV(hue,180,255);
       }
     }

-    offset++;
-    if (offset == repeatEvery) {
-      offset = 0;
-      shift = shift + random8(55,77);
+    hueOffset++;
+    if (hueOffset == repeatEvery) {
+      hueOffset = 0;
+      hueShift = hueShift + random8(55,77);
     }

   } //end_every_n
@@ -73,4 +74,3 @@

 } //end_main_loop
-


Updated timing etc

Updated timing etc

--- quick_release.ino
+++ quick_release.ino
@@ -10,26 +10,41 @@

 // Timing variables
-const int PREDELAY  = 10;     // in ms
-const int STIMDELAY = 250;    // in ms
-const int SHUTTERDELAY = 3;   // in ms
-const int STEPDELAY = 200;    // in µs
-const int EXPOSUREDUR = 500;  // in µs
-const int POSTEXPOSURE = 100; // in ms
+const int PREDELAY  = 10;      // in ms, before stim goes on
+const int STIMDELAY = 250;     // in ms, between stim and shutter
+const int SHUTTERDELAY = 1000; // in µs, between shutter and length
+const int STEPDELAY = 200;     // in µs, between length and camera
+const int EXPOSUREDUR = 100;   // in µs, camera image duration
+const int POSTEXPOSURE = 1000; // in ms, before returning to length

 // Non-global variable declaration
 int stepdelay = STEPDELAY;
 bool run_now = false;

+// ArduTimer Hardware hconfiguration
+#define 1sig = 2;
+#define 1led = 3;
+#define 2sig = 4;
+#define 2led = 5;
+#define 3sig = 6;
+#define 3led = 7;
+#define 4sig = 8;
+#define 4led = 9;
+#define 5sig = 10;
+#define 5led = 11;
+#define 6sig = 12;
+#define 6led = 13;
+
+
 // Pin configuration
-int LEN_OUT    = 2; // to length controller
-int LEN_LED    = 3;
-int SHUT_OUT   = 4; // to quick shutter
-int SHUT_LED   = 5;
-int EXPOSE_OUT = 6; // to exposure trigger
-int EXPOSE_LED = 7;
-int STIM_OUT  = 11; // to stimulus trigger
-int STIM_LED  = 12;
+int LEN_OUT    = 1sig; // to length controller
+int LEN_LED    = 1led;
+int SHUT_OUT   = 4sig; // to quick shutter
+int SHUT_LED   = 4led;
+int EXPOSE_OUT = 5sig; // to exposure trigger
+int EXPOSE_LED = 5led;
+int STIM_OUT   = 3sig; // to stimulus trigger
+int STIM_LED   = 3led;

 // Begin setup of board
 void setup()
@@ -50,14 +65,10 @@
     pinMode(STIM_OUT, OUTPUT);
     pinMode(STIM_LED, OUTPUT);
     // Initial pin states
-    digitalWrite(LEN_OUT, HIGH);
-    digitalWrite(LEN_LED, LOW);
-    digitalWrite(SHUT_OUT, LOW);
-    digitalWrite(SHUT_LED, LOW);
-    digitalWrite(EXPOSE_OUT, LOW);
-    digitalWrite(EXPOSE_LED, LOW);
-    digitalWrite(STIM_OUT, LOW);
-    digitalWrite(STIM_LED, LOW);
+    turn_length(false);
+    turn_stimulus(false);
+    turn_shutter(false);
+    turn_exposure(false);
     // Close out setup
     Serial.println("Setup complete");
 }
@@ -90,25 +101,77 @@
 void run(int predelay, int stimdelay, int shutterdelay, int stepdelay, int exposureduration, int postexposure)
 {
     delay(predelay);
-    digitalWrite(STIM_OUT, HIGH);
-    digitalWrite(STIM_LED, HIGH);
+    turn_stimulus(true);
     delay(stimdelay);
-    digitalWrite(SHUT_OUT, HIGH); // shutter opened before step delay
-    digitalWrite(SHUT_LED, HIGH); // may open during pre-delay in future
-    delay(shutterdelay);
-    digitalWrite(LEN_OUT, LOW);
-    digitalWrite(LEN_LED, HIGH);
+    turn_shutter(true);
+    // shutter opened before step delay
+    // may open during pre-delay in future as latency is established
+    delayMicroseconds(shutterdelay);
+    turn_length(true);
     delayMicroseconds(stepdelay);
-    digitalWrite(EXPOSE_OUT, HIGH);
-    digitalWrite(EXPOSE_LED, HIGH);
+    turn_exposure(true);
     delayMicroseconds(exposureduration);
-    digitalWrite(STIM_OUT, LOW);
-    digitalWrite(STIM_LED, LOW);
-    digitalWrite(EXPOSE_OUT, LOW);
-    digitalWrite(EXPOSE_LED, LOW);
-    digitalWrite(SHUT_OUT, LOW);
-    digitalWrite(SHUT_LED, LOW);
+    turn_stimulus(false);
+    turn_exposure(false);
+    turn_shutter(false);
     delay(postexposure);
-    digitalWrite(LEN_OUT, HIGH);
-    digitalWrite(LEN_LED, LOW);
+    turn_length(false);
 }
+
+// Series of control functions
+/* Each takes a state, true for on and false for off. On and off values for
+   each connection are set here. This is complicated since some need to be
+   high when on while others need to be high when off. To double complicate
+   things, I think that the transistor control shield on the ardutimer inverts
+   the signal.
+
+   NOTE: THESE SHOULD BE DOUBLED CHECKED DURING SET UP.
+*/
+
+// Length control
+void turn_length(boolean state){
+    if(state == true){
+        digitalWrite(LEN_OUT, HIGH);
+        digitalWrite(LEN_LED, HIGH);
+    }
+    else{
+        digitalWrite(LEN_OUT, LOW);
+        digitalWrite(LEN_LED, LOW);
+    }
+}
+
+// Shutter control
+void turn_shutter(boolean state){
+    if(state == true){
+        digitalWrite(SHUT_OUT, LOW);
+        digitalWrite(SHUT_LED, HIGH);
+    }
+    else{
+        digitalWrite(SHUT_OUT, HIGH);
+        digitalWrite(SHUT_LED, LOW);
+    }
+}
+
+//Exposure control
+void turn_exposure(boolean state){
+    if(state == true){
+        digitalWrite(EXPOSE_OUT, LOW);
+        digitalWrite(EXPOSE_LED, HIGH);
+    }
+    else{
+        digitalWrite(EXPOSE_OUT, HIGH);
+        digitalWrite(EXPOSE_LED, LOW);
+    }
+}
+
+//Stimulus control
+void turn_stimulus(boolean state){
+    if(state == true){
+        digitalWrite(STIM_OUT, LOW);
+        digitalWrite(STIM_LED, HIGH);
+    }
+    else{
+        digitalWrite(STIM_OUT, HIGH);
+        digitalWrite(STIM_LED, LOW);
+    }
+}


Arduino prints only on change

Arduino prints only on change


Work on snow animation for three rings of tree

--- Arduino/weather-tree.ino
+++ Arduino/weather-tree.ino
@@ -2,17 +2,33 @@
 #include "RandomPixels.h"

-#define PIN 6
+Adafruit_NeoPixel neopixelRingLarge = Adafruit_NeoPixel(24, 6, WS2812);
+RandomPixels ringLarge = RandomPixels();

+Adafruit_NeoPixel neopixelRingMedium = Adafruit_NeoPixel(16, 7, WS2812);
+RandomPixels ringMedium = RandomPixels();

-Adafruit_NeoPixel snowStrip1 = Adafruit_NeoPixel(24, PIN, WS2812);
-RandomPixels snowRing1 = RandomPixels();
+Adafruit_NeoPixel neopixelRingSmall = Adafruit_NeoPixel(12, 8, WS2812);
+RandomPixels ringSmall = RandomPixels();
+
+// This is the pixel on the top...it will be controlled differently: TODO
+Adafruit_NeoPixel neopixelSingle = Adafruit_NeoPixel(1, 9, WS2812);

 void setup() {

-    snowStrip1.begin();
-    snowStrip1.show();
+    neopixelRingLarge.begin();
+    neopixelRingLarge.show();
+
+    neopixelRingMedium.begin();
+    neopixelRingMedium.show();
+
+    neopixelRingSmall.begin();
+    neopixelRingSmall.show();
+
+    neopixelSingle.begin();
+    neopixelSingle.show();
+
     randomSeed(analogRead(0));

 }
@@ -20,6 +36,9 @@

 void loop() {

-    snowRing1.Animate(snowStrip1, snowStrip1.Color(127, 127, 127), 100);
+    // Snow...make this into function that is callable from API: TODO
+    ringSmall.Animate(neopixelRingLarge, neopixelRingLarge.Color(127, 127, 127), 100);
+    ringMedium.Animate(neopixelRingLarge, neopixelRingLarge.Color(127, 127, 127), 100);
+    ringLarge.Animate(neopixelRingLarge, neopixelRingLarge.Color(127, 127, 127), 100);

 }


Update ProbeCube_v0.98.ino

Update ProbeCube_v0.98.ino

--- Code/ProbeCube_v0.98.ino
+++ Code/ProbeCube_v0.98.ino
@@ -62,7 +62,7 @@
   //指定通訊視窗9600
   Serial.begin(9600);

-  Serial.println("ProbePot is starting");
+  Serial.println("ProbeCube is starting");
   Serial.print("code version: ");
   Serial.println(VERSION);


Docstrings

Docstrings

--- stairs/main.ino
+++ stairs/main.ino
@@ -113,10 +113,12 @@
     return map(analog, 1023, 0, 0, 255);
 }

+// Switch off all LEDs.
 void modeOff() {
     fill_solid(&leds[0], NUM_LEDS, CRGB::Black);
 }

+// Fill all LEDs with the same color. This mode does not have an additional parameter.
 void modeSolid() {
     fill_solid(&leds[0], NUM_LEDS, CHSV(pots.hue, pots.saturation, pots.val));
 }


applied code changes for Simblee code part (@clvsjr9)rom

--- LBridge_RFduino_V09.ino
+++ LBridge_RFduino_V09.ino
@@ -77,11 +77,15 @@
 #include <RFduinoBLE.h>
 #else
 #include <SimbleeBLE.h>
+#include <ota_bootloader.h>
 #endif

 #include <SPI.h>
 #include <Stream.h>
 #include <Memory.h>
+
+// by @clvsjr9 to Arduino 1.6.5 compile
+//#include <data_types.h>

 /* ************************** NFC defines ************************************** */

@@ -1912,7 +1916,7 @@
   if (protocolType == 1) SimbleeBLE.deviceName = LB_NAME;
 #ifdef USE_XBRIDGE2
   Serial.print(" - setting xbridge/wixel device");
-  SimblleBLE.advertisementData = LB_ADVERT;
+  SimbleeBLE.advertisementData = LB_ADVERT;
   SimbleeBLE.customUUID = "0000ffe0-0000-1000-8000-00805f9b34fb";
 #else /* USE_XBRIDGE2 */
   Serial.print(" - setting LimiTTer device");
@@ -2284,8 +2288,12 @@
     #ifdef DEBUG
       Serial.println("V-command received.");
       Serial.println(v);
+    #endif
+    #ifdef RFD
+      RFduinoBLE.send(v.cstr(), v.length());
+    #else
+      SimbleeBLE.send(v.cstr(), v.length());
     #endif
-    RFduinoBLE.send(v.cstr(), v.length());
     displayData();
   }
   if ( toupper(command_buff.commandBuffer[0]) == 'M' ) {
@@ -2296,7 +2304,11 @@
     #ifdef DEBUG
       Serial.println("M-command received.");
     #endif
-    while(!RFduinoBLE.radioActive){}
+    #ifdef RFD
+      while ( RFduinoBLE.radioActive );
+    #else
+      while ( SimbleeBLE.radioActive );
+    #endif
     delay(6);
     eraseData();
     writeData();