Done in principle
This commit is contained in:
parent
d9050dd8b9
commit
3ff23ade8b
@ -46,7 +46,7 @@ void onAlexaChange(EspalexaDevice* dev)
|
|||||||
bri = briLast;
|
bri = briLast;
|
||||||
colorUpdated(NOTIFIER_CALL_MODE_ALEXA);
|
colorUpdated(NOTIFIER_CALL_MODE_ALEXA);
|
||||||
}
|
}
|
||||||
} else applyMacro(macroAlexaOn);
|
} else applyPreset(macroAlexaOn);
|
||||||
} else if (m == EspalexaDeviceProperty::off)
|
} else if (m == EspalexaDeviceProperty::off)
|
||||||
{
|
{
|
||||||
if (!macroAlexaOff)
|
if (!macroAlexaOff)
|
||||||
@ -57,7 +57,7 @@ void onAlexaChange(EspalexaDevice* dev)
|
|||||||
bri = 0;
|
bri = 0;
|
||||||
colorUpdated(NOTIFIER_CALL_MODE_ALEXA);
|
colorUpdated(NOTIFIER_CALL_MODE_ALEXA);
|
||||||
}
|
}
|
||||||
} else applyMacro(macroAlexaOff);
|
} else applyPreset(macroAlexaOff);
|
||||||
} else if (m == EspalexaDeviceProperty::bri)
|
} else if (m == EspalexaDeviceProperty::bri)
|
||||||
{
|
{
|
||||||
bri = espalexaDevice->getValue();
|
bri = espalexaDevice->getValue();
|
||||||
|
@ -11,7 +11,7 @@ void shortPressAction()
|
|||||||
toggleOnOff();
|
toggleOnOff();
|
||||||
colorUpdated(NOTIFIER_CALL_MODE_BUTTON);
|
colorUpdated(NOTIFIER_CALL_MODE_BUTTON);
|
||||||
} else {
|
} else {
|
||||||
applyMacro(macroButton);
|
applyPreset(macroButton);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -41,7 +41,7 @@ void handleButton()
|
|||||||
{
|
{
|
||||||
if (!buttonLongPressed)
|
if (!buttonLongPressed)
|
||||||
{
|
{
|
||||||
if (macroLongPress) {applyMacro(macroLongPress);}
|
if (macroLongPress) {applyPreset(macroLongPress);}
|
||||||
else _setRandomColor(false,true);
|
else _setRandomColor(false,true);
|
||||||
|
|
||||||
buttonLongPressed = true;
|
buttonLongPressed = true;
|
||||||
@ -62,7 +62,7 @@ void handleButton()
|
|||||||
else if (!buttonLongPressed) { //short press
|
else if (!buttonLongPressed) { //short press
|
||||||
if (macroDoublePress)
|
if (macroDoublePress)
|
||||||
{
|
{
|
||||||
if (doublePress) applyMacro(macroDoublePress);
|
if (doublePress) applyPreset(macroDoublePress);
|
||||||
else buttonWaitTime = millis();
|
else buttonWaitTime = millis();
|
||||||
} else shortPressAction();
|
} else shortPressAction();
|
||||||
}
|
}
|
||||||
|
@ -16,7 +16,7 @@ void deserializeConfig() {
|
|||||||
bool fromeep = false;
|
bool fromeep = false;
|
||||||
bool success = deserializeConfigSec();
|
bool success = deserializeConfigSec();
|
||||||
if (!success) { //if file does not exist, try reading from EEPROM
|
if (!success) { //if file does not exist, try reading from EEPROM
|
||||||
loadSettingsFromEEPROM();
|
deEEPSettings();
|
||||||
fromeep = true;
|
fromeep = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -26,7 +26,7 @@ void deserializeConfig() {
|
|||||||
|
|
||||||
success = readObjectFromFile("/cfg.json", nullptr, &doc);
|
success = readObjectFromFile("/cfg.json", nullptr, &doc);
|
||||||
if (!success) { //if file does not exist, try reading from EEPROM
|
if (!success) { //if file does not exist, try reading from EEPROM
|
||||||
if (!fromeep) deEEP();
|
if (!fromeep) deEEPSettings();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -298,17 +298,15 @@ void deserializeConfig() {
|
|||||||
getStringFromJson(otaPass, pwd, 33); //normally not present due to security
|
getStringFromJson(otaPass, pwd, 33); //normally not present due to security
|
||||||
}
|
}
|
||||||
|
|
||||||
DEBUG_PRINTLN(F("Reading settings from /wsec.json..."));
|
//DMX missing!
|
||||||
|
|
||||||
success = readObjectFromFile("/wsec.json", nullptr, &doc);
|
|
||||||
if (!success) { //if file does not exist, try reading from EEPROM
|
|
||||||
loadSettingsFromEEPROM();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void serializeConfig() {
|
void serializeConfig() {
|
||||||
|
DEBUG_PRINTLN(F("Writing settings to /cfg.json..."));
|
||||||
|
|
||||||
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
||||||
|
|
||||||
|
//{ //scope this to reduce stack size
|
||||||
JsonArray rev = doc.createNestedArray("rev");
|
JsonArray rev = doc.createNestedArray("rev");
|
||||||
rev.add(1); //major settings revision
|
rev.add(1); //major settings revision
|
||||||
rev.add(0); //minor settings revision
|
rev.add(0); //minor settings revision
|
||||||
@ -564,14 +562,22 @@ void serializeConfig() {
|
|||||||
ota["lock-wifi"] = wifiLock;
|
ota["lock-wifi"] = wifiLock;
|
||||||
ota["pskl"] = strlen(otaPass);
|
ota["pskl"] = strlen(otaPass);
|
||||||
ota["aota"] = aOtaEnabled;
|
ota["aota"] = aOtaEnabled;
|
||||||
|
//}
|
||||||
|
|
||||||
serializeJson(doc, Serial);
|
File f = WLED_FS.open("/cfg.json", "w");
|
||||||
|
if (f) serializeJson(doc, f);
|
||||||
|
f.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
//settings in /wsec.json, not accessible via webserver, for passwords and tokens
|
//settings in /wsec.json, not accessible via webserver, for passwords and tokens
|
||||||
bool deserializeConfigSec() {
|
bool deserializeConfigSec() {
|
||||||
|
DEBUG_PRINTLN(F("Reading settings from /wsec.json..."));
|
||||||
|
|
||||||
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
||||||
|
|
||||||
|
bool success = readObjectFromFile("/wsec.json", nullptr, &doc);
|
||||||
|
if (!success) return false;
|
||||||
|
|
||||||
JsonObject nw_ins_0 = doc["nw"]["ins"][0];
|
JsonObject nw_ins_0 = doc["nw"]["ins"][0];
|
||||||
getStringFromJson(clientPass, nw_ins_0["psk"], 65);
|
getStringFromJson(clientPass, nw_ins_0["psk"], 65);
|
||||||
|
|
||||||
@ -595,8 +601,40 @@ bool deserializeConfigSec() {
|
|||||||
CJSON(otaLock, ota["lock"]);
|
CJSON(otaLock, ota["lock"]);
|
||||||
CJSON(wifiLock, ota["lock-wifi"]);
|
CJSON(wifiLock, ota["lock-wifi"]);
|
||||||
CJSON(aOtaEnabled, ota["aota"]);
|
CJSON(aOtaEnabled, ota["aota"]);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void serializeConfigSec() {
|
void serializeConfigSec() {
|
||||||
|
DEBUG_PRINTLN(F("Writing settings to /wsec.json..."));
|
||||||
|
|
||||||
|
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
||||||
|
|
||||||
|
JsonObject nw = doc.createNestedObject("nw");
|
||||||
|
|
||||||
|
JsonArray nw_ins = nw.createNestedArray("ins");
|
||||||
|
|
||||||
|
JsonObject nw_ins_0 = nw_ins.createNestedObject();
|
||||||
|
nw_ins_0["psk"] = clientPass;
|
||||||
|
|
||||||
|
JsonObject ap = doc.createNestedObject("ap");
|
||||||
|
ap["psk"] = apPass;
|
||||||
|
|
||||||
|
JsonObject interfaces = doc.createNestedObject("if");
|
||||||
|
JsonObject if_blynk = interfaces.createNestedObject("blynk");
|
||||||
|
if_blynk["token"] = blynkApiKey;
|
||||||
|
JsonObject if_mqtt = interfaces.createNestedObject("mqtt");
|
||||||
|
if_mqtt["psk"] = mqttPass;
|
||||||
|
JsonObject if_hue = interfaces.createNestedObject("hue");
|
||||||
|
if_hue["key"] = hueApiKey;
|
||||||
|
|
||||||
|
JsonObject ota = doc.createNestedObject("ota");
|
||||||
|
ota["pwd"] = otaPass;
|
||||||
|
ota["lock"] = otaLock;
|
||||||
|
ota["lock-wifi"] = wifiLock;
|
||||||
|
ota["aota"] = aOtaEnabled;
|
||||||
|
|
||||||
|
File f = WLED_FS.open("/wsec.json", "w");
|
||||||
|
if (f) serializeJson(doc, f);
|
||||||
|
f.close();
|
||||||
}
|
}
|
@ -145,8 +145,6 @@
|
|||||||
#define NL_MODE_COLORFADE 2 //Fade to target brightness and secondary color gradually
|
#define NL_MODE_COLORFADE 2 //Fade to target brightness and secondary color gradually
|
||||||
#define NL_MODE_SUN 3 //Sunrise/sunset. Target brightness is set immediately, then Sunrise effect is started. Max 60 min.
|
#define NL_MODE_SUN 3 //Sunrise/sunset. Target brightness is set immediately, then Sunrise effect is started. Max 60 min.
|
||||||
|
|
||||||
//EEPROM size
|
|
||||||
#define EEPSIZE 2560 //Maximum is 4096
|
|
||||||
|
|
||||||
#define NTP_PACKET_SIZE 48
|
#define NTP_PACKET_SIZE 48
|
||||||
|
|
||||||
|
@ -147,6 +147,11 @@ void setCronixie();
|
|||||||
void _overlayCronixie();
|
void _overlayCronixie();
|
||||||
void _drawOverlayCronixie();
|
void _drawOverlayCronixie();
|
||||||
|
|
||||||
|
//presets.cpp
|
||||||
|
bool applyPreset(byte index);
|
||||||
|
void savePreset(byte index, bool persist = true, const char* pname = nullptr, JsonObject saveobj = JsonObject());
|
||||||
|
void deletePreset(byte index);
|
||||||
|
|
||||||
//set.cpp
|
//set.cpp
|
||||||
void _setRandomColor(bool _sec,bool fromButton=false);
|
void _setRandomColor(bool _sec,bool fromButton=false);
|
||||||
bool isAsterisksOnly(const char* str, byte maxLen);
|
bool isAsterisksOnly(const char* str, byte maxLen);
|
||||||
@ -201,19 +206,7 @@ void userConnected();
|
|||||||
void userLoop();
|
void userLoop();
|
||||||
|
|
||||||
//wled_eeprom.cpp
|
//wled_eeprom.cpp
|
||||||
void commit();
|
|
||||||
void clearEEPROM();
|
|
||||||
void writeStringToEEPROM(uint16_t pos, char* str, uint16_t len);
|
|
||||||
void readStringFromEEPROM(uint16_t pos, char* str, uint16_t len);
|
|
||||||
void saveSettingsToEEPROM();
|
|
||||||
void loadSettingsFromEEPROM();
|
|
||||||
void savedToPresets();
|
|
||||||
bool applyPreset(byte index);
|
|
||||||
void savePreset(byte index, bool persist = true, const char* pname = nullptr, JsonObject saveobj = JsonObject());
|
|
||||||
void deletePreset(byte index);
|
|
||||||
void loadMacro(byte index, char* m);
|
|
||||||
void applyMacro(byte index);
|
void applyMacro(byte index);
|
||||||
void saveMacro(byte index, const String& mc, bool persist = true); //only commit on single save, not in settings
|
|
||||||
void deEEP();
|
void deEEP();
|
||||||
void deEEPSettings();
|
void deEEPSettings();
|
||||||
|
|
||||||
|
@ -13,7 +13,7 @@ void handleHue()
|
|||||||
colorUpdated(NOTIFIER_CALL_MODE_HUE); hueReceived = false;
|
colorUpdated(NOTIFIER_CALL_MODE_HUE); hueReceived = false;
|
||||||
if (hueStoreAllowed && hueNewKey)
|
if (hueStoreAllowed && hueNewKey)
|
||||||
{
|
{
|
||||||
saveSettingsToEEPROM(); //save api key
|
serializeConfigSec(); //save api key
|
||||||
hueStoreAllowed = false;
|
hueStoreAllowed = false;
|
||||||
hueNewKey = false;
|
hueNewKey = false;
|
||||||
}
|
}
|
||||||
|
@ -29,7 +29,7 @@ bool decodeIRCustom(uint32_t code)
|
|||||||
{
|
{
|
||||||
//just examples, feel free to modify or remove
|
//just examples, feel free to modify or remove
|
||||||
case IRCUSTOM_ONOFF : toggleOnOff(); break;
|
case IRCUSTOM_ONOFF : toggleOnOff(); break;
|
||||||
case IRCUSTOM_MACRO1 : applyMacro(1); break;
|
case IRCUSTOM_MACRO1 : applyPreset(1); break;
|
||||||
|
|
||||||
default: return false;
|
default: return false;
|
||||||
}
|
}
|
||||||
|
@ -282,7 +282,7 @@ void handleNightlight()
|
|||||||
}
|
}
|
||||||
updateBlynk();
|
updateBlynk();
|
||||||
if (macroNl > 0)
|
if (macroNl > 0)
|
||||||
applyMacro(macroNl);
|
applyPreset(macroNl);
|
||||||
nightlightActiveOld = false;
|
nightlightActiveOld = false;
|
||||||
}
|
}
|
||||||
} else if (nightlightActiveOld) //early de-init
|
} else if (nightlightActiveOld) //early de-init
|
||||||
|
72
wled00/presets.cpp
Normal file
72
wled00/presets.cpp
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
#include "wled.h"
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Methods to handle saving and loading presets to/from the filesystem
|
||||||
|
*/
|
||||||
|
|
||||||
|
bool applyPreset(byte index)
|
||||||
|
{
|
||||||
|
if (fileDoc) {
|
||||||
|
errorFlag = readObjectFromFileUsingId("/presets.json", index, fileDoc) ? ERR_NONE : ERR_FS_PLOAD;
|
||||||
|
#ifdef WLED_DEBUG_FS
|
||||||
|
serializeJson(*fileDoc, Serial);
|
||||||
|
#endif
|
||||||
|
deserializeState(fileDoc->as<JsonObject>());
|
||||||
|
} else {
|
||||||
|
DEBUGFS_PRINTLN(F("Make read buf"));
|
||||||
|
DynamicJsonDocument fDoc(JSON_BUFFER_SIZE);
|
||||||
|
errorFlag = readObjectFromFileUsingId("/presets.json", index, &fDoc) ? ERR_NONE : ERR_FS_PLOAD;
|
||||||
|
#ifdef WLED_DEBUG_FS
|
||||||
|
serializeJson(fDoc, Serial);
|
||||||
|
#endif
|
||||||
|
deserializeState(fDoc.as<JsonObject>());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!errorFlag) {
|
||||||
|
currentPreset = index;
|
||||||
|
isPreset = true;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void savePreset(byte index, bool persist, const char* pname, JsonObject saveobj)
|
||||||
|
{
|
||||||
|
if (index == 0) return;
|
||||||
|
bool docAlloc = fileDoc;
|
||||||
|
JsonObject sObj = saveobj;
|
||||||
|
|
||||||
|
if (!docAlloc) {
|
||||||
|
DEBUGFS_PRINTLN(F("Allocating saving buffer"));
|
||||||
|
fileDoc = new DynamicJsonDocument(JSON_BUFFER_SIZE);
|
||||||
|
sObj = fileDoc->to<JsonObject>();
|
||||||
|
if (pname) sObj["n"] = pname;
|
||||||
|
} else {
|
||||||
|
DEBUGFS_PRINTLN(F("Reuse recv buffer"));
|
||||||
|
sObj.remove(F("psave"));
|
||||||
|
sObj.remove(F("v"));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!sObj["o"]) {
|
||||||
|
DEBUGFS_PRINTLN(F("Save current state"));
|
||||||
|
serializeState(sObj, true, sObj["ib"], sObj["sb"]);
|
||||||
|
currentPreset = index;
|
||||||
|
}
|
||||||
|
sObj.remove("o");
|
||||||
|
sObj.remove("ib");
|
||||||
|
sObj.remove("sb");
|
||||||
|
sObj.remove(F("error"));
|
||||||
|
sObj.remove(F("time"));
|
||||||
|
|
||||||
|
writeObjectToFileUsingId("/presets.json", index, fileDoc);
|
||||||
|
if (!docAlloc) delete fileDoc;
|
||||||
|
presetsModifiedTime = now(); //unix time
|
||||||
|
updateFSInfo();
|
||||||
|
}
|
||||||
|
|
||||||
|
void deletePreset(byte index) {
|
||||||
|
StaticJsonDocument<24> empty;
|
||||||
|
writeObjectToFileUsingId("/presets.json", index, &empty);
|
||||||
|
presetsModifiedTime = now(); //unix time
|
||||||
|
updateFSInfo();
|
||||||
|
}
|
@ -233,13 +233,6 @@ void handleSettingsSet(AsyncWebServerRequest *request, byte subPage)
|
|||||||
countdownMin = request->arg(F("CM")).toInt();
|
countdownMin = request->arg(F("CM")).toInt();
|
||||||
countdownSec = request->arg(F("CS")).toInt();
|
countdownSec = request->arg(F("CS")).toInt();
|
||||||
|
|
||||||
for (int i=1;i<17;i++)
|
|
||||||
{
|
|
||||||
String a = "M"+String(i);
|
|
||||||
if (request->hasArg(a.c_str())) saveMacro(i,request->arg(a),false);
|
|
||||||
}
|
|
||||||
|
|
||||||
macroBoot = request->arg(F("MB")).toInt();
|
|
||||||
macroAlexaOn = request->arg(F("A0")).toInt();
|
macroAlexaOn = request->arg(F("A0")).toInt();
|
||||||
macroAlexaOff = request->arg(F("A1")).toInt();
|
macroAlexaOff = request->arg(F("A1")).toInt();
|
||||||
macroButton = request->arg(F("MP")).toInt();
|
macroButton = request->arg(F("MP")).toInt();
|
||||||
@ -272,7 +265,7 @@ void handleSettingsSet(AsyncWebServerRequest *request, byte subPage)
|
|||||||
{
|
{
|
||||||
if (request->hasArg(F("RS"))) //complete factory reset
|
if (request->hasArg(F("RS"))) //complete factory reset
|
||||||
{
|
{
|
||||||
clearEEPROM();
|
WLED_FS.format();
|
||||||
serveMessage(request, 200, F("All Settings erased."), F("Connect to WLED-AP to setup again"),255);
|
serveMessage(request, 200, F("All Settings erased."), F("Connect to WLED-AP to setup again"),255);
|
||||||
doReboot = true;
|
doReboot = true;
|
||||||
}
|
}
|
||||||
@ -327,7 +320,7 @@ void handleSettingsSet(AsyncWebServerRequest *request, byte subPage)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
if (subPage != 6 || !doReboot) saveSettingsToEEPROM(); //do not save if factory reset
|
if (subPage != 6 || !doReboot) serializeConfig(); //do not save if factory reset
|
||||||
if (subPage == 2) {
|
if (subPage == 2) {
|
||||||
strip.init(useRGBW,ledCount,skipFirstLed);
|
strip.init(useRGBW,ledCount,skipFirstLed);
|
||||||
}
|
}
|
||||||
@ -382,31 +375,6 @@ bool handleSet(AsyncWebServerRequest *request, const String& req, bool apply)
|
|||||||
DEBUG_PRINT(F("API req: "));
|
DEBUG_PRINT(F("API req: "));
|
||||||
DEBUG_PRINTLN(req);
|
DEBUG_PRINTLN(req);
|
||||||
|
|
||||||
//write presets and macros saved to flash directly?
|
|
||||||
bool persistSaves = true;
|
|
||||||
pos = req.indexOf(F("NP"));
|
|
||||||
if (pos > 0) {
|
|
||||||
persistSaves = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
//save macro, requires &MS=<slot>(<macro>) format
|
|
||||||
pos = req.indexOf(F("&MS="));
|
|
||||||
if (pos > 0) {
|
|
||||||
int i = req.substring(pos + 4).toInt();
|
|
||||||
pos = req.indexOf('(') +1;
|
|
||||||
if (pos > 0) {
|
|
||||||
int en = req.indexOf(')');
|
|
||||||
String mc = req.substring(pos);
|
|
||||||
if (en > 0) mc = req.substring(pos, en);
|
|
||||||
saveMacro(i, mc, persistSaves);
|
|
||||||
}
|
|
||||||
|
|
||||||
pos = req.indexOf(F("IN"));
|
|
||||||
if (pos < 1) XML_response(request);
|
|
||||||
return true;
|
|
||||||
//if you save a macro in one request, other commands in that request are ignored due to unwanted behavior otherwise
|
|
||||||
}
|
|
||||||
|
|
||||||
strip.applyToAllSelected = true;
|
strip.applyToAllSelected = true;
|
||||||
|
|
||||||
//segment select (sets main segment)
|
//segment select (sets main segment)
|
||||||
@ -591,10 +559,10 @@ bool handleSet(AsyncWebServerRequest *request, const String& req, bool apply)
|
|||||||
overlayCurrent = getNumVal(&req, pos);
|
overlayCurrent = getNumVal(&req, pos);
|
||||||
}
|
}
|
||||||
|
|
||||||
//apply macro
|
//apply macro (deprecated, added for compatibility with pre-0.11 automations)
|
||||||
pos = req.indexOf(F("&M="));
|
pos = req.indexOf(F("&M="));
|
||||||
if (pos > 0) {
|
if (pos > 0) {
|
||||||
applyMacro(getNumVal(&req, pos));
|
applyPreset(getNumVal(&req, pos) + 16);
|
||||||
}
|
}
|
||||||
|
|
||||||
//toggle send UDP direct notifications
|
//toggle send UDP direct notifications
|
||||||
|
@ -141,17 +141,6 @@ void WLED::loop()
|
|||||||
|
|
||||||
void WLED::setup()
|
void WLED::setup()
|
||||||
{
|
{
|
||||||
EEPROM.begin(EEPSIZE);
|
|
||||||
ledCount = EEPROM.read(229) + ((EEPROM.read(398) << 8) & 0xFF00);
|
|
||||||
if (ledCount > MAX_LEDS || ledCount == 0)
|
|
||||||
ledCount = 30;
|
|
||||||
|
|
||||||
#ifdef ESP8266
|
|
||||||
#if LEDPIN == 3
|
|
||||||
if (ledCount > MAX_LEDS_DMA)
|
|
||||||
ledCount = MAX_LEDS_DMA; // DMA method uses too much ram
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
Serial.begin(115200);
|
Serial.begin(115200);
|
||||||
Serial.setTimeout(50);
|
Serial.setTimeout(50);
|
||||||
DEBUG_PRINTLN();
|
DEBUG_PRINTLN();
|
||||||
@ -206,8 +195,6 @@ void WLED::setup()
|
|||||||
showWelcomePage = true;
|
showWelcomePage = true;
|
||||||
WiFi.persistent(false);
|
WiFi.persistent(false);
|
||||||
|
|
||||||
if (macroBoot > 0)
|
|
||||||
applyMacro(macroBoot);
|
|
||||||
Serial.println(F("Ada"));
|
Serial.println(F("Ada"));
|
||||||
|
|
||||||
// generate module IDs
|
// generate module IDs
|
||||||
@ -252,6 +239,16 @@ void WLED::setup()
|
|||||||
void WLED::beginStrip()
|
void WLED::beginStrip()
|
||||||
{
|
{
|
||||||
// Initialize NeoPixel Strip and button
|
// Initialize NeoPixel Strip and button
|
||||||
|
#ifdef ESP8266
|
||||||
|
#if LEDPIN == 3
|
||||||
|
if (ledCount > MAX_LEDS_DMA)
|
||||||
|
ledCount = MAX_LEDS_DMA; // DMA method uses too much ram
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (ledCount > MAX_LEDS || ledCount == 0)
|
||||||
|
ledCount = 30;
|
||||||
|
|
||||||
strip.init(useRGBW, ledCount, skipFirstLed);
|
strip.init(useRGBW, ledCount, skipFirstLed);
|
||||||
strip.setBrightness(0);
|
strip.setBrightness(0);
|
||||||
strip.setShowCallback(handleOverlayDraw);
|
strip.setShowCallback(handleOverlayDraw);
|
||||||
|
@ -2,12 +2,16 @@
|
|||||||
#include "wled.h"
|
#include "wled.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
* DEPRECATED, do not use for new settings
|
||||||
|
* Only used to restore config from pre-0.11 installations using the deEEP() methods
|
||||||
|
*
|
||||||
* Methods to handle saving and loading to non-volatile memory
|
* Methods to handle saving and loading to non-volatile memory
|
||||||
* EEPROM Map: https://github.com/Aircoookie/WLED/wiki/EEPROM-Map
|
* EEPROM Map: https://github.com/Aircoookie/WLED/wiki/EEPROM-Map
|
||||||
*/
|
*/
|
||||||
|
|
||||||
//eeprom Version code, enables default settings instead of 0 init on update
|
//eeprom Version code, enables default settings instead of 0 init on update
|
||||||
#define EEPVER 22
|
#define EEPVER 22
|
||||||
|
#define EEPSIZE 2560 //Maximum is 4096
|
||||||
//0 -> old version, default
|
//0 -> old version, default
|
||||||
//1 -> 0.4p 1711272 and up
|
//1 -> 0.4p 1711272 and up
|
||||||
//2 -> 0.4p 1711302 and up
|
//2 -> 0.4p 1711302 and up
|
||||||
@ -32,34 +36,6 @@
|
|||||||
//21-> 0.10.1p
|
//21-> 0.10.1p
|
||||||
//22-> 2009260
|
//22-> 2009260
|
||||||
|
|
||||||
void commit()
|
|
||||||
{
|
|
||||||
if (!EEPROM.commit()) errorFlag = ERR_EEP_COMMIT;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Erase all configuration data
|
|
||||||
*/
|
|
||||||
void clearEEPROM()
|
|
||||||
{
|
|
||||||
for (int i = 0; i < EEPSIZE; i++)
|
|
||||||
{
|
|
||||||
EEPROM.write(i, 0);
|
|
||||||
}
|
|
||||||
commit();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void writeStringToEEPROM(uint16_t pos, char* str, uint16_t len)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < len; ++i)
|
|
||||||
{
|
|
||||||
EEPROM.write(pos + i, str[i]);
|
|
||||||
if (str[i] == 0) return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void readStringFromEEPROM(uint16_t pos, char* str, uint16_t len)
|
void readStringFromEEPROM(uint16_t pos, char* str, uint16_t len)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < len; ++i)
|
for (int i = 0; i < len; ++i)
|
||||||
@ -70,228 +46,6 @@ void readStringFromEEPROM(uint16_t pos, char* str, uint16_t len)
|
|||||||
str[len] = 0; //make sure every string is properly terminated. str must be at least len +1 big.
|
str[len] = 0; //make sure every string is properly terminated. str must be at least len +1 big.
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Write configuration to flash
|
|
||||||
*/
|
|
||||||
void saveSettingsToEEPROM()
|
|
||||||
{
|
|
||||||
if (EEPROM.read(233) != 233) //set no first boot flag
|
|
||||||
{
|
|
||||||
clearEEPROM();
|
|
||||||
EEPROM.write(233, 233);
|
|
||||||
}
|
|
||||||
|
|
||||||
writeStringToEEPROM( 0, clientSSID, 32);
|
|
||||||
writeStringToEEPROM( 32, clientPass, 64);
|
|
||||||
writeStringToEEPROM( 96, cmDNS, 32);
|
|
||||||
writeStringToEEPROM(128, apSSID, 32);
|
|
||||||
writeStringToEEPROM(160, apPass, 64);
|
|
||||||
|
|
||||||
EEPROM.write(224, nightlightDelayMinsDefault);
|
|
||||||
EEPROM.write(225, nightlightMode);
|
|
||||||
EEPROM.write(226, notifyDirectDefault);
|
|
||||||
EEPROM.write(227, apChannel);
|
|
||||||
EEPROM.write(228, apHide);
|
|
||||||
EEPROM.write(229, ledCount & 0xFF);
|
|
||||||
EEPROM.write(230, notifyButton);
|
|
||||||
EEPROM.write(231, notifyTwice);
|
|
||||||
EEPROM.write(232, buttonEnabled);
|
|
||||||
//233 reserved for first boot flag
|
|
||||||
|
|
||||||
for (int i = 0; i<4; i++) //ip addresses
|
|
||||||
{
|
|
||||||
EEPROM.write(234+i, staticIP[i]);
|
|
||||||
EEPROM.write(238+i, staticGateway[i]);
|
|
||||||
EEPROM.write(242+i, staticSubnet[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
EEPROM.write(249, briS);
|
|
||||||
|
|
||||||
EEPROM.write(250, receiveNotificationBrightness);
|
|
||||||
EEPROM.write(251, fadeTransition);
|
|
||||||
EEPROM.write(252, strip.reverseMode);
|
|
||||||
EEPROM.write(253, transitionDelayDefault & 0xFF);
|
|
||||||
EEPROM.write(254, (transitionDelayDefault >> 8) & 0xFF);
|
|
||||||
EEPROM.write(255, briMultiplier);
|
|
||||||
|
|
||||||
//255,250,231,230,226 notifier bytes
|
|
||||||
writeStringToEEPROM(256, otaPass, 32);
|
|
||||||
|
|
||||||
EEPROM.write(288, nightlightTargetBri);
|
|
||||||
EEPROM.write(289, otaLock);
|
|
||||||
EEPROM.write(290, udpPort & 0xFF);
|
|
||||||
EEPROM.write(291, (udpPort >> 8) & 0xFF);
|
|
||||||
writeStringToEEPROM(292, serverDescription, 32);
|
|
||||||
|
|
||||||
EEPROM.write(327, ntpEnabled);
|
|
||||||
EEPROM.write(328, currentTimezone);
|
|
||||||
EEPROM.write(329, useAMPM);
|
|
||||||
EEPROM.write(330, strip.gammaCorrectBri);
|
|
||||||
EEPROM.write(331, strip.gammaCorrectCol);
|
|
||||||
EEPROM.write(332, overlayDefault);
|
|
||||||
|
|
||||||
EEPROM.write(333, alexaEnabled);
|
|
||||||
writeStringToEEPROM(334, alexaInvocationName, 32);
|
|
||||||
EEPROM.write(366, notifyAlexa);
|
|
||||||
|
|
||||||
EEPROM.write(367, (arlsOffset>=0));
|
|
||||||
EEPROM.write(368, abs(arlsOffset));
|
|
||||||
EEPROM.write(369, turnOnAtBoot);
|
|
||||||
|
|
||||||
EEPROM.write(370, noWifiSleep);
|
|
||||||
|
|
||||||
EEPROM.write(372, useRGBW);
|
|
||||||
EEPROM.write(374, strip.paletteFade);
|
|
||||||
EEPROM.write(375, strip.milliampsPerLed); //was apWaitTimeSecs up to 0.8.5
|
|
||||||
EEPROM.write(376, apBehavior);
|
|
||||||
|
|
||||||
EEPROM.write(377, EEPVER); //eeprom was updated to latest
|
|
||||||
|
|
||||||
EEPROM.write(378, udpPort2 & 0xFF);
|
|
||||||
EEPROM.write(379, (udpPort2 >> 8) & 0xFF);
|
|
||||||
|
|
||||||
EEPROM.write(382, strip.paletteBlend);
|
|
||||||
EEPROM.write(383, strip.colorOrder);
|
|
||||||
|
|
||||||
EEPROM.write(385, irEnabled);
|
|
||||||
|
|
||||||
EEPROM.write(387, strip.ablMilliampsMax & 0xFF);
|
|
||||||
EEPROM.write(388, (strip.ablMilliampsMax >> 8) & 0xFF);
|
|
||||||
EEPROM.write(389, bootPreset);
|
|
||||||
EEPROM.write(390, aOtaEnabled);
|
|
||||||
EEPROM.write(391, receiveNotificationColor);
|
|
||||||
EEPROM.write(392, receiveNotificationEffects);
|
|
||||||
EEPROM.write(393, wifiLock);
|
|
||||||
|
|
||||||
EEPROM.write(394, abs(utcOffsetSecs) & 0xFF);
|
|
||||||
EEPROM.write(395, (abs(utcOffsetSecs) >> 8) & 0xFF);
|
|
||||||
EEPROM.write(396, (utcOffsetSecs<0)); //is negative
|
|
||||||
EEPROM.write(397, syncToggleReceive);
|
|
||||||
EEPROM.write(398, (ledCount >> 8) & 0xFF);
|
|
||||||
//EEPROM.write(399, was !enableSecTransition);
|
|
||||||
|
|
||||||
//favorite setting (preset) memory (25 slots/ each 20byte)
|
|
||||||
//400 - 940 reserved
|
|
||||||
writeStringToEEPROM(990, ntpServerName, 32);
|
|
||||||
|
|
||||||
EEPROM.write(2048, huePollingEnabled);
|
|
||||||
//EEPROM.write(2049, hueUpdatingEnabled);
|
|
||||||
for (int i = 2050; i < 2054; ++i)
|
|
||||||
{
|
|
||||||
EEPROM.write(i, hueIP[i-2050]);
|
|
||||||
}
|
|
||||||
writeStringToEEPROM(2054, hueApiKey, 46);
|
|
||||||
EEPROM.write(2100, huePollIntervalMs & 0xFF);
|
|
||||||
EEPROM.write(2101, (huePollIntervalMs >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2102, notifyHue);
|
|
||||||
EEPROM.write(2103, hueApplyOnOff);
|
|
||||||
EEPROM.write(2104, hueApplyBri);
|
|
||||||
EEPROM.write(2105, hueApplyColor);
|
|
||||||
EEPROM.write(2106, huePollLightId);
|
|
||||||
|
|
||||||
EEPROM.write(2150, overlayMin);
|
|
||||||
EEPROM.write(2151, overlayMax);
|
|
||||||
EEPROM.write(2152, analogClock12pixel);
|
|
||||||
EEPROM.write(2153, analogClock5MinuteMarks);
|
|
||||||
EEPROM.write(2154, analogClockSecondsTrail);
|
|
||||||
|
|
||||||
EEPROM.write(2155, countdownMode);
|
|
||||||
EEPROM.write(2156, countdownYear);
|
|
||||||
EEPROM.write(2157, countdownMonth);
|
|
||||||
EEPROM.write(2158, countdownDay);
|
|
||||||
EEPROM.write(2159, countdownHour);
|
|
||||||
EEPROM.write(2160, countdownMin);
|
|
||||||
EEPROM.write(2161, countdownSec);
|
|
||||||
setCountdown();
|
|
||||||
|
|
||||||
writeStringToEEPROM(2165, cronixieDisplay, 6);
|
|
||||||
EEPROM.write(2171, cronixieBacklight);
|
|
||||||
setCronixie();
|
|
||||||
|
|
||||||
EEPROM.write(2175, macroBoot);
|
|
||||||
EEPROM.write(2176, macroAlexaOn);
|
|
||||||
EEPROM.write(2177, macroAlexaOff);
|
|
||||||
EEPROM.write(2178, macroButton);
|
|
||||||
EEPROM.write(2179, macroLongPress);
|
|
||||||
EEPROM.write(2180, macroCountdown);
|
|
||||||
EEPROM.write(2181, macroNl);
|
|
||||||
EEPROM.write(2182, macroDoublePress);
|
|
||||||
|
|
||||||
#ifdef WLED_ENABLE_DMX
|
|
||||||
EEPROM.write(2185, e131ProxyUniverse & 0xFF);
|
|
||||||
EEPROM.write(2186, (e131ProxyUniverse >> 8) & 0xFF);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
EEPROM.write(2187, e131Port & 0xFF);
|
|
||||||
EEPROM.write(2188, (e131Port >> 8) & 0xFF);
|
|
||||||
|
|
||||||
EEPROM.write(2189, e131SkipOutOfSequence);
|
|
||||||
EEPROM.write(2190, e131Universe & 0xFF);
|
|
||||||
EEPROM.write(2191, (e131Universe >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2192, e131Multicast);
|
|
||||||
EEPROM.write(2193, realtimeTimeoutMs & 0xFF);
|
|
||||||
EEPROM.write(2194, (realtimeTimeoutMs >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2195, arlsForceMaxBri);
|
|
||||||
EEPROM.write(2196, arlsDisableGammaCorrection);
|
|
||||||
EEPROM.write(2197, DMXAddress & 0xFF);
|
|
||||||
EEPROM.write(2198, (DMXAddress >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2199, DMXMode);
|
|
||||||
|
|
||||||
EEPROM.write(2200, !receiveDirect);
|
|
||||||
EEPROM.write(2201, notifyMacro); //was enableRealtime
|
|
||||||
EEPROM.write(2203, strip.rgbwMode);
|
|
||||||
EEPROM.write(2204, skipFirstLed);
|
|
||||||
|
|
||||||
if (saveCurrPresetCycConf)
|
|
||||||
{
|
|
||||||
EEPROM.write(2205, presetCyclingEnabled);
|
|
||||||
EEPROM.write(2206, presetCycleTime & 0xFF);
|
|
||||||
EEPROM.write(2207, (presetCycleTime >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2208, presetCycleMin);
|
|
||||||
EEPROM.write(2209, presetCycleMax);
|
|
||||||
// was EEPROM.write(2210, presetApplyBri);
|
|
||||||
// was EEPROM.write(2211, presetApplyCol);
|
|
||||||
// was EEPROM.write(2212, presetApplyFx);
|
|
||||||
saveCurrPresetCycConf = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
writeStringToEEPROM(2220, blynkApiKey, 35);
|
|
||||||
|
|
||||||
for (int i = 0; i < 8; ++i)
|
|
||||||
{
|
|
||||||
EEPROM.write(2260 + i, timerHours[i] );
|
|
||||||
EEPROM.write(2270 + i, timerMinutes[i]);
|
|
||||||
EEPROM.write(2280 + i, timerWeekday[i]);
|
|
||||||
EEPROM.write(2290 + i, timerMacro[i] );
|
|
||||||
}
|
|
||||||
|
|
||||||
EEPROM.write(2299, mqttEnabled);
|
|
||||||
writeStringToEEPROM(2300, mqttServer, 32);
|
|
||||||
writeStringToEEPROM(2333, mqttDeviceTopic, 32);
|
|
||||||
writeStringToEEPROM(2366, mqttGroupTopic, 32);
|
|
||||||
writeStringToEEPROM(2399, mqttUser, 40);
|
|
||||||
writeStringToEEPROM(2440, mqttPass, 40);
|
|
||||||
writeStringToEEPROM(2481, mqttClientID, 40);
|
|
||||||
EEPROM.write(2522, mqttPort & 0xFF);
|
|
||||||
EEPROM.write(2523, (mqttPort >> 8) & 0xFF);
|
|
||||||
|
|
||||||
// DMX (2530 - 2549)
|
|
||||||
#ifdef WLED_ENABLE_DMX
|
|
||||||
EEPROM.write(2530, DMXChannels);
|
|
||||||
EEPROM.write(2531, DMXGap & 0xFF);
|
|
||||||
EEPROM.write(2532, (DMXGap >> 8) & 0xFF);
|
|
||||||
EEPROM.write(2533, DMXStart & 0xFF);
|
|
||||||
EEPROM.write(2534, (DMXStart >> 8) & 0xFF);
|
|
||||||
|
|
||||||
for (int i=0; i<15; i++) {
|
|
||||||
EEPROM.write(2535+i, DMXFixtureMap[i]);
|
|
||||||
} // last used: 2549. maybe leave a few bytes for future expansion and go on with 2600 kthxbye.
|
|
||||||
#endif
|
|
||||||
|
|
||||||
commit();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Read all configuration from flash
|
* Read all configuration from flash
|
||||||
*/
|
*/
|
||||||
@ -299,9 +53,7 @@ void loadSettingsFromEEPROM()
|
|||||||
{
|
{
|
||||||
if (EEPROM.read(233) != 233) //first boot/reset to default
|
if (EEPROM.read(233) != 233) //first boot/reset to default
|
||||||
{
|
{
|
||||||
DEBUG_PRINT("Settings invalid, restoring defaults...");
|
DEBUG_PRINTLN(F("EEPROM settings invalid, using defaults..."));
|
||||||
saveSettingsToEEPROM();
|
|
||||||
DEBUG_PRINTLN("done");
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
int lastEEPROMversion = EEPROM.read(377); //last EEPROM version before update
|
int lastEEPROMversion = EEPROM.read(377); //last EEPROM version before update
|
||||||
@ -597,186 +349,12 @@ void loadSettingsFromEEPROM()
|
|||||||
//2944 - 3071 reserved for Usermods (need to increase EEPSIZE to 3072 in const.h)
|
//2944 - 3071 reserved for Usermods (need to increase EEPSIZE to 3072 in const.h)
|
||||||
|
|
||||||
overlayCurrent = overlayDefault;
|
overlayCurrent = overlayDefault;
|
||||||
|
|
||||||
savedToPresets();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//PRESET PROTOCOL 20 bytes
|
//provided for increased compatibility with usermods written for v0.10
|
||||||
//0: preset purpose byte 0:invalid 1:valid preset 2:segment preset 2.0
|
void applyMacro(byte index) {
|
||||||
//1:a 2:r 3:g 4:b 5:w 6:er 7:eg 8:eb 9:ew 10:fx 11:sx | custom chase 12:numP 13:numS 14:(0:fs 1:both 2:fe) 15:step 16:ix 17: fp 18-19:Zeros
|
applyPreset(index+16);
|
||||||
//determines which presets already contain save data
|
|
||||||
void savedToPresets()
|
|
||||||
{
|
|
||||||
for (byte index = 1; index < 16; index++)
|
|
||||||
{
|
|
||||||
uint16_t i = 380 + index*20;
|
|
||||||
|
|
||||||
if (EEPROM.read(i) == 1) {
|
|
||||||
savedPresets |= 0x01 << (index-1);
|
|
||||||
} else
|
|
||||||
{
|
|
||||||
savedPresets &= ~(0x01 << (index-1));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (EEPROM.read(700) == 2 || EEPROM.read(700) == 3) {
|
|
||||||
savedPresets |= 0x01 << 15;
|
|
||||||
} else
|
|
||||||
{
|
|
||||||
savedPresets &= ~(0x01 << 15);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool applyPreset(byte index)
|
|
||||||
{
|
|
||||||
if (fileDoc) {
|
|
||||||
errorFlag = readObjectFromFileUsingId("/presets.json", index, fileDoc) ? ERR_NONE : ERR_FS_PLOAD;
|
|
||||||
#ifdef WLED_DEBUG_FS
|
|
||||||
serializeJson(*fileDoc, Serial);
|
|
||||||
#endif
|
|
||||||
deserializeState(fileDoc->as<JsonObject>());
|
|
||||||
} else {
|
|
||||||
DEBUGFS_PRINTLN(F("Make read buf"));
|
|
||||||
DynamicJsonDocument fDoc(JSON_BUFFER_SIZE);
|
|
||||||
errorFlag = readObjectFromFileUsingId("/presets.json", index, &fDoc) ? ERR_NONE : ERR_FS_PLOAD;
|
|
||||||
#ifdef WLED_DEBUG_FS
|
|
||||||
serializeJson(fDoc, Serial);
|
|
||||||
#endif
|
|
||||||
deserializeState(fDoc.as<JsonObject>());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!errorFlag) {
|
|
||||||
currentPreset = index;
|
|
||||||
isPreset = true;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
/*if (index == 255 || index == 0)
|
|
||||||
{
|
|
||||||
loadSettingsFromEEPROM(false);//load boot defaults
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (index > 16 || index < 1) return false;
|
|
||||||
uint16_t i = 380 + index*20;
|
|
||||||
byte ver = EEPROM.read(i);
|
|
||||||
|
|
||||||
if (index < 16) {
|
|
||||||
if (ver != 1) return false;
|
|
||||||
strip.applyToAllSelected = true;
|
|
||||||
if (loadBri) bri = EEPROM.read(i+1);
|
|
||||||
|
|
||||||
for (byte j=0; j<4; j++)
|
|
||||||
{
|
|
||||||
col[j] = EEPROM.read(i+j+2);
|
|
||||||
colSec[j] = EEPROM.read(i+j+6);
|
|
||||||
}
|
|
||||||
strip.setColor(2, EEPROM.read(i+12), EEPROM.read(i+13), EEPROM.read(i+14), EEPROM.read(i+15)); //tertiary color
|
|
||||||
|
|
||||||
effectCurrent = EEPROM.read(i+10);
|
|
||||||
effectSpeed = EEPROM.read(i+11);
|
|
||||||
effectIntensity = EEPROM.read(i+16);
|
|
||||||
effectPalette = EEPROM.read(i+17);
|
|
||||||
} else {
|
|
||||||
if (ver != 2 && ver != 3) return false;
|
|
||||||
strip.applyToAllSelected = false;
|
|
||||||
if (loadBri) bri = EEPROM.read(i+1);
|
|
||||||
WS2812FX::Segment* seg = strip.getSegments();
|
|
||||||
memcpy(seg, EEPROM.getDataPtr() +i+2, 240);
|
|
||||||
if (ver == 2) { //versions before 2004230 did not have opacity
|
|
||||||
for (byte j = 0; j < strip.getMaxSegments(); j++)
|
|
||||||
{
|
|
||||||
strip.getSegment(j).opacity = 255;
|
|
||||||
strip.getSegment(j).setOption(SEG_OPTION_ON, 1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
setValuesFromMainSeg();
|
|
||||||
}
|
|
||||||
currentPreset = index;
|
|
||||||
isPreset = true;
|
|
||||||
return true;*/
|
|
||||||
}
|
|
||||||
|
|
||||||
void savePreset(byte index, bool persist, const char* pname, JsonObject saveobj)
|
|
||||||
{
|
|
||||||
if (index == 0) return;
|
|
||||||
bool docAlloc = fileDoc;
|
|
||||||
JsonObject sObj = saveobj;
|
|
||||||
|
|
||||||
if (!docAlloc) {
|
|
||||||
DEBUGFS_PRINTLN(F("Allocating saving buffer"));
|
|
||||||
fileDoc = new DynamicJsonDocument(JSON_BUFFER_SIZE);
|
|
||||||
sObj = fileDoc->to<JsonObject>();
|
|
||||||
if (pname) sObj["n"] = pname;
|
|
||||||
} else {
|
|
||||||
DEBUGFS_PRINTLN(F("Reuse recv buffer"));
|
|
||||||
sObj.remove(F("psave"));
|
|
||||||
sObj.remove(F("v"));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!sObj["o"]) {
|
|
||||||
DEBUGFS_PRINTLN(F("Save current state"));
|
|
||||||
serializeState(sObj, true, sObj["ib"], sObj["sb"]);
|
|
||||||
currentPreset = index;
|
|
||||||
}
|
|
||||||
sObj.remove("o");
|
|
||||||
sObj.remove("ib");
|
|
||||||
sObj.remove("sb");
|
|
||||||
sObj.remove(F("error"));
|
|
||||||
sObj.remove(F("time"));
|
|
||||||
|
|
||||||
writeObjectToFileUsingId("/presets.json", index, fileDoc);
|
|
||||||
if (!docAlloc) delete fileDoc;
|
|
||||||
presetsModifiedTime = now(); //unix time
|
|
||||||
updateFSInfo();
|
|
||||||
}
|
|
||||||
|
|
||||||
void deletePreset(byte index) {
|
|
||||||
StaticJsonDocument<24> empty;
|
|
||||||
writeObjectToFileUsingId("/presets.json", index, &empty);
|
|
||||||
presetsModifiedTime = now(); //unix time
|
|
||||||
updateFSInfo();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void loadMacro(byte index, char* m)
|
|
||||||
{
|
|
||||||
index-=1;
|
|
||||||
if (index > 15) return;
|
|
||||||
readStringFromEEPROM(1024+64*index, m, 64);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void applyMacro(byte index)
|
|
||||||
{
|
|
||||||
index-=1;
|
|
||||||
if (index > 15) return;
|
|
||||||
String mc="win&";
|
|
||||||
char m[65];
|
|
||||||
loadMacro(index+1, m);
|
|
||||||
mc += m;
|
|
||||||
mc += "&IN"; //internal, no XML response
|
|
||||||
if (!notifyMacro) mc += "&NN";
|
|
||||||
String forbidden = "&M="; //dont apply if called by the macro itself to prevent loop
|
|
||||||
/*
|
|
||||||
* NOTE: loop is still possible if you call a different macro from a macro, which then calls the first macro again.
|
|
||||||
* To prevent that, but also disable calling macros within macros, comment the next line out.
|
|
||||||
*/
|
|
||||||
forbidden = forbidden + index;
|
|
||||||
if (mc.indexOf(forbidden) >= 0) return;
|
|
||||||
handleSet(nullptr, mc);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void saveMacro(byte index, const String& mc, bool persist) //only commit on single save, not in settings
|
|
||||||
{
|
|
||||||
index-=1;
|
|
||||||
if (index > 15) return;
|
|
||||||
int s = 1024+index*64;
|
|
||||||
for (int i = s; i < s+64; i++)
|
|
||||||
{
|
|
||||||
EEPROM.write(i, mc.charAt(i-s));
|
|
||||||
}
|
|
||||||
if (persist) commit();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -388,16 +388,7 @@ void getSettingsJS(byte subPage, char* dest)
|
|||||||
sappend('v',SET_F("CH"),countdownHour);
|
sappend('v',SET_F("CH"),countdownHour);
|
||||||
sappend('v',SET_F("CM"),countdownMin);
|
sappend('v',SET_F("CM"),countdownMin);
|
||||||
sappend('v',SET_F("CS"),countdownSec);
|
sappend('v',SET_F("CS"),countdownSec);
|
||||||
char k[4]; k[0]= 'M';
|
|
||||||
for (int i=1;i<17;i++)
|
|
||||||
{
|
|
||||||
char m[65];
|
|
||||||
loadMacro(i, m);
|
|
||||||
sprintf(k+1,"%i",i);
|
|
||||||
sappends('s',k,m);
|
|
||||||
}
|
|
||||||
|
|
||||||
sappend('v',SET_F("MB"),macroBoot);
|
|
||||||
sappend('v',SET_F("A0"),macroAlexaOn);
|
sappend('v',SET_F("A0"),macroAlexaOn);
|
||||||
sappend('v',SET_F("A1"),macroAlexaOff);
|
sappend('v',SET_F("A1"),macroAlexaOff);
|
||||||
sappend('v',SET_F("MP"),macroButton);
|
sappend('v',SET_F("MP"),macroButton);
|
||||||
@ -406,6 +397,7 @@ void getSettingsJS(byte subPage, char* dest)
|
|||||||
sappend('v',SET_F("MN"),macroNl);
|
sappend('v',SET_F("MN"),macroNl);
|
||||||
sappend('v',SET_F("MD"),macroDoublePress);
|
sappend('v',SET_F("MD"),macroDoublePress);
|
||||||
|
|
||||||
|
char k[4];
|
||||||
k[2] = 0; //Time macros
|
k[2] = 0; //Time macros
|
||||||
for (int i = 0; i<8; i++)
|
for (int i = 0; i<8; i++)
|
||||||
{
|
{
|
||||||
|
Loading…
Reference in New Issue
Block a user