If RAM usage is excessive on a 32u4 it not only can cause the program to crash, it can render the chip un-programmable.
The Keypad Controller stores the display strings and codes in EEPROM. Achieving all 61 codes requires using the EEPROM almost completely.
Two programs are required; This EEPROM program is run only once and then is overwritten by the Service program.
The Service program gets from the EEROM only the information it needs for the current set of letter and decimal values, which is only 59 bytes. The Service program determines how to use this data.
//EEPROMwrite.ino for Keypad-Control.ino. John Saunders 6/24/2024
#include <EEPROM.h>
#define NUM_AREAS 9
#define LINETWO_QTY 5
struct stats_t {
int lastAddr; //Filled in Setup()
int areasStart; //Filled in Setup()
int line2Start; //Filled in Setup()
uint8_t numItems; //Filled in Setup()
uint8_t decKey = 0; //These two are written by KeypadControl
uint8_t areaInx = 0; //before power off,and read back at setup().
};
stats_t stats;
typedef char area_t[18];
const area_t areas[NUM_AREAS] =
{
"L.R. Display", // 0
"L.R. Big Dial", // 1
"Cube Alarm Box", // 2
"L.R. Ornament", // 3
"L.R. Lights", // 4
"Clear Box Outlets", // 5
"Gazebo Controller", // 6
"Garage Controls", // 7
"Portable Devices" // 8
};
typedef char lineTwo_t[18];
const lineTwo_t lineTwoData[LINETWO_QTY] = {
// 0 1 2 3 4
{"Blue NightTime"},{"Power Down"},{"Sound-LED OFF"},{"All Lights Off"},{"*=OFF,#=ON"}
};
struct dispLine_t {
char offCode;
char onCode;
byte areaInx; //Index into areas
byte lineTwoInx; //Index into lineTwo
char itemName[16];
};
const dispLine_t dispLines[] = {
// 0 1 2 3 4
{ 'C','F',0,0,"Temperatures"},{'D','F',0,0,"Humidities"},{'A','F',0,0,"Garage Stats"},{'E','F',0,0,"Baro & Solar"},{'B','F',0,0,"Solar battery V"},
// 5 6 7 8 9
{'a','n',1,1,"Room Temps"},{'c','n',1,1,"Patio Temps"},{'b','n',1,1,"Room Humidity"},{'d','n',1,1,"Patio Humidity"},{'g','n',1,1,"Gas Quality"},
// 10 11
{'e','n',1,1,"Solar Curent"},{'f','p',1,3,"Barometer"},
// 12 13 14 15 16 17
{'H','A',2,2,"Red LED ON"},{'H','D',2,2,"Green LED ON"},{'H','e',2,2,"Blue LED ON"},{'H','B',2,2,"Play BaBa"},{'H','Q',2,2,"Play Chime"},{'H','h',2,2,"Play Siren"},
// 18 19 20
{'9','d',3,4,"Circle Display"},{'W','Y',3,4,"Flashing Disp"},{'g','M',3,4,"Missions Lights"},
// 21 22 23 14
{'f','b',4,4,"Reading Lamp"},{'C','I',4,4,"Hanging Lamp"},{'G','R',4,4,"Ceiling Lights"},{'8','K',4,4,"Pineapple Light"},
// 25 26
{'F','E',4,4,"Wall unit shelf"},{'U','S',4,4,"Speaker Display"},
// 27 28 29
{'J','m',5,4,"Eves LED String"},{'N','X',5,4,"Clear Box tip"}, {'4','5',6,4,"Top Light"},
// 30 31 32 33
{'6','7',6,4,"LED String"},{'2','3',6,4,"Cherub Fountain"},{'0','1',6,4,"Owl Fountain"},{'V','L',6,4,"28V Socket"},
// 34 35 36
{'k','i',7,4,"Pole Lamp"}, {'c','a',8,4,"Flower Receiver"},{'l','P',8,4,"One Outlet Box"}
};
void setup() {
int eeAddress;
char marker;
int inx = 0;
//dispLines, areas and lineTwoData are written consecutively from 0
do {
eeAddress = (sizeof(dispLine_t) * inx);
EEPROM.put(eeAddress, dispLines[inx]); //Starts at 0
delay(10);
marker = dispLines[inx].onCode;
inx++;
} while (marker != 'P'); //Change if more than one area 8 made
stats.numItems = inx;
eeAddress += sizeof(dispLine_t);
stats.areasStart = eeAddress;
for (inx = 0; inx < NUM_AREAS; inx++) {
eeAddress = (sizeof(area_t) * inx) + stats.areasStart;
EEPROM.put(eeAddress, areas[inx]);
delay(10);
}
eeAddress += sizeof(area_t);
stats.line2Start = eeAddress;
for (inx = 0; inx < LINETWO_QTY; inx++) {
eeAddress = (sizeof(lineTwo_t) * inx) + stats.line2Start;
EEPROM.put(eeAddress, lineTwoData[inx]);
delay(10);
}
stats.lastAddr = eeAddress += sizeof(lineTwo_t);
EEPROM.put(1010,stats); //Fiixed adress, must be copied into keyboard control
}
void loop() {
/* Empty loop */
}