diff --git a/platformio.ini b/platformio.ini index c7ef6c7..4248499 100644 --- a/platformio.ini +++ b/platformio.ini @@ -78,7 +78,7 @@ lib_deps = build_flags = -D APP=StarBase -D PIOENV=$PIOENV - -D VERSION=24110513 ; Date and time (GMT!), update at every commit!! + -D VERSION=24110711 ; Date and time (GMT!), update at every commit!! -D LFS_THREADSAFE ; enables use of semaphores in LittleFS driver -D STARBASE_DEVMODE -mtext-section-literals ;otherwise [UserModLive::setup()]+0xa17): dangerous relocation: l32r: literal target out of range (try using text-section-literals) diff --git a/src/App/AppModDemo.h b/src/App/AppModDemo.h index 5fef41c..8362121 100644 --- a/src/App/AppModDemo.h +++ b/src/App/AppModDemo.h @@ -25,7 +25,7 @@ class AppModDemo: public SysModule { parentVar = ui->initAppMod(parentVar, name, 1100); - JsonObject currentVar = ui->initCheckBox(parentVar, "on", true, false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject currentVar = ui->initCheckBox(parentVar, "on", true, false, [](EventArguments) { switch (eventType) { //varFun case onChange: //implement on/off behaviour return true; @@ -34,7 +34,7 @@ class AppModDemo: public SysModule { currentVar["dash"] = true; //logarithmic slider (10) - currentVar = ui->initSlider(parentVar, "brightness", 10, 0, 255, false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + currentVar = ui->initSlider(parentVar, "brightness", 10, 0, 255, false, [](EventArguments) { switch (eventType) { //varFun case onChange: { return true; } default: return false; @@ -44,13 +44,13 @@ class AppModDemo: public SysModule { ui->initText(parentVar, "textField", "text"); - ui->initPin(parentVar, "blinkPin", &blinkPin, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPin(parentVar, "blinkPin", &blinkPin, false, [this](EventArguments) { switch (eventType) { //varFun case onUI: - ui->setComment(var, "šŸš§ tbd: reserved and allocated pins"); + variable.setComment("šŸš§ tbd: reserved and allocated pins"); return true; case onChange: { //deallocate old value... - uint8_t oldValue = var["oldValue"]; + uint8_t oldValue = variable.var["oldValue"]; ppf("blinkPin onChange %d %d\n", oldValue, blinkPin); if (oldValue != UINT8_MAX) pinsM->deallocatePin(oldValue, "Blink"); diff --git a/src/Sys/SysModFiles.cpp b/src/Sys/SysModFiles.cpp index 88adc5d..452e245 100644 --- a/src/Sys/SysModFiles.cpp +++ b/src/Sys/SysModFiles.cpp @@ -30,14 +30,14 @@ void SysModFiles::setup() { SysModule::setup(); parentVar = ui->initSysMod(parentVar, name, 2101); - JsonObject tableVar = ui->initTable(parentVar, "files", nullptr, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = ui->initTable(parentVar, "files", nullptr, false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "List of files"); + variable.setComment("List of files"); return true; case onDelete: if (rowNr != UINT8_MAX && rowNr < fileNames.size()) { const char * fileName = fileNames[rowNr].s; - // ppf("files onDelete %s[%d] = %s %s\n", Variable(var).id(), rowNr, Variable(var).valueString().c_str(), fileName); + // ppf("files onDelete %s[%d] = %s %s\n", variable.id(), rowNr, variable.valueString().c_str(), fileName); this->removeFiles(fileName, false); #ifdef STARBASE_USERMOD_LIVE @@ -58,12 +58,12 @@ void SysModFiles::setup() { ui->initNumber(tableVar, "size", &fileSizes, 0, UINT16_MAX, true); - // ui->initURL(tableVar, "flLink", nullptr, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + // ui->initURL(tableVar, "flLink", nullptr, true, [this](EventArguments) { switch (eventType) { // case onSetValue: // for (size_t rowNr = 0; rowNr < fileList.size(); rowNr++) { // char urlString[32] = "file/"; // strlcat(urlString, fileList[rowNr].name, sizeof(urlString)); - // mdl->setValue(var, JsonString(urlString, JsonString::Copied), rowNr); + // mdl->setValue(variable.var, JsonString(urlString, JsonString::Copied), rowNr); // } // return true; // default: return false; @@ -76,10 +76,10 @@ void SysModFiles::setup() { ui->initFileUpload(parentVar, "upload");//, nullptr, UINT16_MAX, false); - ui->initProgress(parentVar, "totalSize", 0, 0, files->totalBytes(), true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initProgress(parentVar, "totalSize", 0, 0, files->totalBytes(), true, [](EventArguments) { switch (eventType) { case onChange: - var["max"] = files->totalBytes(); //makes sense? - web->addResponse(var, "comment", "%d / %d B", files->usedBytes(), files->totalBytes()); + variable.var["max"] = files->totalBytes(); //makes sense? + web->addResponse(variable.var, "comment", "%d / %d B", files->usedBytes(), files->totalBytes()); return true; default: return false; }}); diff --git a/src/Sys/SysModInstances.h b/src/Sys/SysModInstances.h index 8da939a..84cec6f 100644 --- a/src/Sys/SysModInstances.h +++ b/src/Sys/SysModInstances.h @@ -116,99 +116,99 @@ class SysModInstances:public SysModule { JsonObject tableVar = ui->initTable(parentVar, "instances", nullptr, true); - ui->initText(tableVar, "name", nullptr, 32, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "name", nullptr, 32, false, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, JsonString(instances[rowNrL].name, JsonString::Copied), rowNrL); + mdl->setValue(variable.var, JsonString(instances[rowNrL].name, JsonString::Copied), rowNrL); return true; // comment this out for the time being as causes corrupted instance names // case onChange: - // strlcpy(instances[rowNr].name, mdl->getValue(var, rowNr), sizeof(instances[rowNr].name)); - // sendMessageUDP(instances[rowNr].ip, "name", mdl->getValue(var, rowNr)); + // strlcpy(instances[rowNr].name, mdl->getValue(variable.var, rowNr), sizeof(instances[rowNr].name)); + // sendMessageUDP(instances[rowNr].ip, "name", mdl->getValue(variable.var, rowNr)); // return true; default: return false; }}); - ui->initURL(tableVar, "show", nullptr, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initURL(tableVar, "show", nullptr, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) { char urlString[32] = "http://"; strlcat(urlString, instances[rowNrL].ip.toString().c_str(), sizeof(urlString)); - mdl->setValue(var, JsonString(urlString, JsonString::Copied), rowNrL); + mdl->setValue(variable.var, JsonString(urlString, JsonString::Copied), rowNrL); } return true; default: return false; }}); - ui->initNumber(tableVar, "link", UINT16_MAX, 0, UINT16_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "link", UINT16_MAX, 0, UINT16_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, calcGroup(instances[rowNrL].name), rowNrL); + mdl->setValue(variable.var, calcGroup(instances[rowNrL].name), rowNrL); return true; default: return false; }}); - ui->initText(tableVar, "IP", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "IP", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, JsonString(instances[rowNrL].ip.toString().c_str(), JsonString::Copied), rowNrL); + mdl->setValue(variable.var, JsonString(instances[rowNrL].ip.toString().c_str(), JsonString::Copied), rowNrL); return true; default: return false; }}); - ui->initText(tableVar, "type", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "type", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) { byte type = instances[rowNrL].sysData.type; - mdl->setValue(var, (type==0)?"WLED":(type==1)?"StarBase":(type==2)?"StarLight":(type==3)?"StarLedsLive":"StarFork", rowNrL); + mdl->setValue(variable.var, (type==0)?"WLED":(type==1)?"StarBase":(type==2)?"StarLight":(type==3)?"StarLedsLive":"StarFork", rowNrL); } return true; default: return false; }}); - ui->initNumber(tableVar, "version", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "version", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].version, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].version, rowNrL); return true; default: return false; }}); - ui->initNumber(tableVar, "uptime", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "uptime", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].sysData.uptime, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].sysData.uptime, rowNrL); return true; default: return false; }}); - ui->initNumber(tableVar, "now", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "now", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].sysData.now / 1000, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].sysData.now / 1000, rowNrL); return true; default: return false; }}); - ui->initNumber(tableVar, "timestamp", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "timestamp", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].sysData.timeSource, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].sysData.timeSource, rowNrL); return true; default: return false; }}); - ui->initNumber(tableVar, "time", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "time", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].sysData.tokiTime, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].sysData.tokiTime, rowNrL); return true; default: return false; }}); - ui->initNumber(tableVar, "ms", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "ms", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) - mdl->setValue(var, instances[rowNrL].sysData.tokiMs, rowNrL); + mdl->setValue(variable.var, instances[rowNrL].sysData.tokiMs, rowNrL); return true; default: return false; }}); @@ -225,32 +225,32 @@ class SysModInstances:public SysModule { JsonObject insVar; // = ui->cloneVar(var, columnVarID, [this, var](JsonObject insVar){}); //create a var of the same type. InitVar is not calling onChange which is good in this situation! - insVar = ui->initVar(tableVar, columnVarID, var["type"], false, [this, var](JsonObject insVar, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + insVar = ui->initVar(tableVar, columnVarID, var["type"], false, [this, var](Variable insVariable, uint8_t rowNr, uint8_t eventType) { switch (eventType) { //varEvent case onSetValue: //should not trigger onChange for (size_t rowNrL = 0; rowNrL < instances.size() && (rowNr == UINT8_MAX || rowNrL == rowNr); rowNrL++) { - // ppf("initVar dash %s[%d]\n", Variable(insVar).id(), rowNrL); + // ppf("initVar dash %s[%d]\n", variable.id(), rowNrL); //do what setValue is doing except calling onChange - // insVar["value"][rowNrL] = instances[rowNrL].jsonData[Variable(var).id()]; //only int values... + // insVar["value"][rowNrL] = instances[rowNrL].jsonData[variable.id()]; //only int values... - web->addResponse(insVar, "value", instances[rowNrL].jsonData[Variable(var).id()], rowNrL); + web->addResponse(insVariable.var, "value", instances[rowNrL].jsonData[Variable(var).id()], rowNrL); - // mdl->setValue(insVar, instances[rowNrL].jsonData[Variable(var).id()], rowNr); + // mdl->setValue(insVariable.var, instances[rowNrL].jsonData[Variable(var).id()], rowNr); //send to ws? } return true; case onUI: // call onUI of the base variable for the new variable - mdl->varFunctions[var["fun"]](insVar, rowNr, onUI); + mdl->varEvents[var["fun"]](insVariable, rowNr, onUI); return true; case onChange: { //do not set this initially!!! if (rowNr != UINT8_MAX) { //if this instance update directly, otherwise send over network if (instances[rowNr].ip == net->localIP()) { - mdl->setValue(var, mdl->getValue(insVar, rowNr).as()); //this will call sendDataWS (tbd...), do not set for rowNr + mdl->setValue(var, mdl->getValue(insVariable.var, rowNr).as()); //this will call sendDataWS (tbd...), do not set for rowNr } else { - sendMessageUDP(instances[rowNr].ip, var, mdl->getValue(insVar, rowNr)); + sendMessageUDP(instances[rowNr].ip, var, mdl->getValue(insVariable.var, rowNr)); } } // print->printJson(" ", var); @@ -603,7 +603,7 @@ class SysModInstances:public SysModule { instance.jsonData.to(); //clear //send dash values - mdl->findVars("dash", true, [&instance](JsonObject var) { //varFun + mdl->findVars("dash", true, [&instance](JsonObject var) { //varEvent instance.jsonData[Variable(var).id()] = var["value"]; // // print->printJson("setVar", var); // JsonArray valArray = Variable(var).valArray(); diff --git a/src/Sys/SysModModel.cpp b/src/Sys/SysModModel.cpp index 530534f..682772c 100644 --- a/src/Sys/SysModModel.cpp +++ b/src/Sys/SysModModel.cpp @@ -18,9 +18,9 @@ String Variable::valueString(uint8_t rowNr) { if (rowNr == UINT8_MAX) - return var["value"].as(); + return value().as(); else - return var["value"][rowNr].as(); + return value()[rowNr].as(); } void Variable::removeValuesForRow(uint8_t rowNr) { @@ -111,7 +111,7 @@ } else { if (childVariable.order() < 0) { //if not updated - // childVar["value"] = (char*)0; + // childVariable.value() = (char*)0; ppf("varPostDetails %s.%s <- null\n", id(), childVariable.id()); // setValue(var, -99, rowNr); //set value -99 // childVariable.order(-childVariable.order()); @@ -130,9 +130,9 @@ web->getResponseObject()["details"]["var"] = var; } - bool Variable::triggerEvent(uint8_t funType, uint8_t rowNr, bool init) { + bool Variable::triggerEvent(uint8_t eventType, uint8_t rowNr, bool init) { - if (funType == onChange) { + if (eventType == onChange) { if (!init) { if (!var["dash"].isNull()) instances->changedVarsQueue.push_back(var); //tbd: check value arrays / rowNr is working @@ -142,9 +142,9 @@ if (!var["p"].isNull()) { JsonVariant value; if (rowNr == UINT8_MAX) { - value = var["value"]; + value = this->value(); } else { - value = var["value"][rowNr]; + value = this->value(rowNr); } //pointer is an array if set by setValueRowNr, used for controls as each control has a seperate variable @@ -157,7 +157,7 @@ if (pointer != 0) { - if (var["value"].is() && !isPointerArray) { //vector if val array but not if control (each var in array stored in seperate variable) + if (this->value().is() && !isPointerArray) { //vector if val array but not if control (each var in array stored in seperate variable) if (rowNr != UINT8_MAX) { //pointer checks if (var["type"] == "select" || var["type"] == "range" || var["type"] == "pin") { @@ -220,10 +220,10 @@ // const char *valuePointer = (const char *)pointer; // if (valuePointer != nullptr) { // *valuePointer = value; - // ppf("pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", Variable(var).id(), *valuePointer, valuePointer, rowNr, var["value"].as().c_str(), pointer); + // ppf("pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", id(), *valuePointer, valuePointer, rowNr, valueString().c_str(), pointer); // } // else - // ppf("dev pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", Variable(var).id(), *valuePointer, valuePointer, rowNr, var["value"].as().c_str(), pointer); + // ppf("dev pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", id(), *valuePointer, valuePointer, rowNr, valueString().c_str(), pointer); // } } else @@ -234,40 +234,40 @@ bool result = false; - //call varFun if exists + //call varEvent if exists if (!var["fun"].isNull()) {//isNull needed here! size_t funNr = var["fun"]; - if (funNr < mdl->varFunctions.size()) { - result = mdl->varFunctions[funNr](var, rowNr, funType); + if (funNr < mdl->varEvents.size()) { + result = mdl->varEvents[funNr](*this, rowNr, eventType); if (result && !readOnly()) { //send rowNr = 0 if no rowNr //only print vars with a value and not onSetValue as that changes a lot due to instances clients etc (tbd) //don't print if onSetValue or oldValue is null - if (funType != onSetValue && (!var["oldValue"].isNull() || ((rowNr != UINT8_MAX) && !var["oldValue"][rowNr].isNull()))) { - ppf("%sFun %s.%s", funType==onSetValue?"val":funType==onUI?"ui":funType==onChange?"ch":funType==onAdd?"add":funType==onDelete?"del":"other", pid(), id()); + if (eventType != onSetValue && (!var["oldValue"].isNull() || ((rowNr != UINT8_MAX) && !var["oldValue"][rowNr].isNull()))) { + ppf("%sEvent %s.%s", eventType==onSetValue?"val":eventType==onUI?"ui":eventType==onChange?"ch":eventType==onAdd?"add":eventType==onDelete?"del":"other", pid(), id()); if (rowNr != UINT8_MAX) { ppf("[%d] (", rowNr); - if (funType == onChange) ppf("%s ->", var["oldValue"][rowNr].as().c_str()); - ppf("%s)\n", var["value"][rowNr].as().c_str()); + if (eventType == onChange) ppf("%s ->", var["oldValue"][rowNr].as().c_str()); + ppf("%s)\n", valueString().c_str()); } else { ppf(" ("); - if (funType == onChange) ppf("%s ->", var["oldValue"].as().c_str()); + if (eventType == onChange) ppf("%s ->", var["oldValue"].as().c_str()); ppf("%s)\n", valueString().c_str()); } } - } //varFun exists + } //varEvent exists } else - ppf("dev triggerEvent function nr %s.%s outside bounds %d >= %d\n", pid(), id(), funNr, mdl->varFunctions.size()); - } //varFun exists + ppf("dev triggerEvent function nr %s.%s outside bounds %d >= %d\n", pid(), id(), funNr, mdl->varEvents.size()); + } //varEvent exists //delete pointers after calling var.onDelete as var.onDelete might need the values - if (funType == onAdd || funType == onDelete) { + if (eventType == onAdd || eventType == onDelete) { print->printJson("triggerEvent add/del", var); //if delete, delete also from vector ... //find the columns of the table - if (funType == onDelete) { + if (eventType == onDelete) { for (JsonObject childVar: children()) { int pointer; if (childVar["p"].is()) @@ -306,16 +306,83 @@ } } } //onDelete - web->getResponseObject()[funType==onAdd?"onAdd":"onDelete"]["rowNr"] = rowNr; + web->getResponseObject()[eventType==onAdd?"onAdd":"onDelete"]["rowNr"] = rowNr; print->printJson("triggerEvent add/del response", web->getResponseObject()); } //onAdd onDelete //for ro variables, call onSetValue to add also the value in responseDoc (as it is not stored in the model) - if (funType == onUI && readOnly()) { + if (eventType == onUI && readOnly()) { triggerEvent(onSetValue, rowNr); } - return result; //varFun exists + return result; //varEvent exists + } + + void Variable::setLabel(const char * text) { + web->addResponse(var, "label", text); + } + void Variable::setComment(const char * text) { + web->addResponse(var, "comment", text); + } + JsonArray Variable::setOptions() { + JsonObject responseObject = web->getResponseObject(); + char pidid[64]; + print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); + return responseObject[pidid]["options"].to(); + } + //return the options from onUI (don't forget to clear responseObject) + JsonArray Variable::getOptions() { + triggerEvent(onUI); //rebuild options + char pidid[64]; + print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); + return web->getResponseObject()[pidid]["options"]; + } + void Variable::clearOptions() { + char pidid[64]; + print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); + web->getResponseObject()[pidid].remove("options"); + } + + //find options text in a hierarchy of options + void Variable::findOptionsText(uint8_t value, char * groupName, char * optionName) { + uint8_t startValue = 0; + char pidid[64]; + print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); + bool optionsExisted = !web->getResponseObject()[pidid]["options"].isNull(); + JsonString groupNameJS; + JsonString optionNameJS; + JsonArray options = getOptions(); + if (!findOptionsTextRec(options, &startValue, value, &groupNameJS, &optionNameJS)) + ppf("findOptions select option not found %d %s %s\n", value, groupNameJS.isNull()?"X":groupNameJS.c_str(), optionNameJS.isNull()?"X":optionNameJS.c_str()); + strlcpy(groupName, groupNameJS.c_str(), 32); //groupName is char[32] + strlcpy(optionName, optionNameJS.c_str(), 32); //optionName is char[32] + if (!optionsExisted) + clearOptions(); //if created here then also remove + } + + // (groupName and optionName as pointers? String is already a pointer?) + bool Variable::findOptionsTextRec(JsonVariant options, uint8_t * startValue, uint8_t value, JsonString *groupName, JsonString *optionName, JsonString parentGroup) { + if (options.is()) { //array of options + for (JsonVariant option : options.as()) { + if (findOptionsTextRec(option, startValue, value, groupName, optionName, parentGroup)) + return true; + } + } + else if (options.is()) { //group + for (JsonPair pair: options.as()) { + if (findOptionsTextRec(pair.value(), startValue, value, groupName, optionName, parentGroup.isNull()?pair.key():parentGroup)) //send the master level group name only + return true; + } + } else { //individual option + if (*startValue == value) { + *groupName = parentGroup; + *optionName = options.as(); + ppf("Found %d=%d ? %s . %s\n", *startValue, value, (*groupName).isNull()?"":(*groupName).c_str(), (*optionName).isNull()?"":(*optionName).c_str()); + return true; + } + (*startValue)++; + } + return false; } SysModModel::SysModModel() :SysModule("Model") { @@ -338,9 +405,9 @@ void SysModModel::setup() { parentVar = ui->initSysMod(parentVar, name, 4303); parentVar["s"] = true; //setup - ui->initButton(parentVar, "saveModel", false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initButton(parentVar, "saveModel", false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Write to model.json"); + variable.setComment("Write to model.json"); return true; case onChange: doWriteModel = true; @@ -350,16 +417,16 @@ void SysModModel::setup() { #ifdef STARBASE_DEVMODE - ui->initCheckBox(parentVar, "showObsolete", false, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(parentVar, "showObsolete", false, false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Show in UI (refresh)"); + variable.setComment("Show in UI (refresh)"); return true; default: return false; }}); - ui->initButton(parentVar, "deleteObsolete", false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initButton(parentVar, "deleteObsolete", false, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Delete obsolete variables šŸš§"); + variable.setComment("Delete obsolete variables šŸš§"); return true; // case onChange: // model->to(); //create @@ -444,7 +511,7 @@ void SysModModel::cleanUpModel(JsonObject parent, bool oPos, bool ro) { //remove ro values (ro vars cannot be deleted as SM uses these vars) // remove if var is ro or table is instance table (exception here, values don't need to be saved) - if (ro && (parent["id"] == "instances" || variable.readOnly())) {// && !var["value"].isNull()) + if (ro && (parent["id"] == "instances" || variable.readOnly())) {// && !value().isNull()) // ppf("remove ro value %s\n", variable.id()); var.remove("value"); } diff --git a/src/Sys/SysModModel.h b/src/Sys/SysModModel.h index d5433b7..244a547 100644 --- a/src/Sys/SysModModel.h +++ b/src/Sys/SysModModel.h @@ -214,6 +214,9 @@ class Variable { const char * pid() {return var["pid"];} const char * id() {return var["id"]; } + JsonVariant value() {return var["value"];} + JsonVariant value(uint8_t rowNr) {return var["value"][rowNr];} + String valueString(uint8_t rowNr = UINT8_MAX); int order() {return var["o"];} @@ -240,13 +243,29 @@ class Variable { void postDetails(uint8_t rowNr); - //checks if var has fun of type funType implemented by calling it and checking result (for onUI on RO var, also onSetValue is called) + //checks if var has fun of type eventType implemented by calling it and checking result (for onUI on RO var, also onSetValue is called) //onChange: sends dash var change to udp (if init), sets pointer if pointer var and run onChange - bool triggerEvent(uint8_t funType = onSetValue, uint8_t rowNr = UINT8_MAX, bool init = false); + bool triggerEvent(uint8_t eventType = onSetValue, uint8_t rowNr = UINT8_MAX, bool init = false); + + void setLabel(const char * text); + void setComment(const char * text); + JsonArray setOptions(); + //return the options from onUI (don't forget to clear responseObject) + JsonArray getOptions(); + void clearOptions(); + + //find options text in a hierarchy of options + void findOptionsText(uint8_t value, char * groupName, char * optionName); + + // (groupName and optionName as pointers? String is already a pointer?) + bool findOptionsTextRec(JsonVariant options, uint8_t * startValue, uint8_t value, JsonString *groupName, JsonString *optionName, JsonString parentGroup = JsonString()); + }; //class Variable +#define EventArguments Variable variable, uint8_t rowNr, uint8_t eventType + // https://stackoverflow.com/questions/59111610/how-do-you-declare-a-lambda-function-using-typedef-and-then-use-it-by-passing-to -typedef std::function VarFun; +typedef std::function VarEvent; class SysModModel:public SysModule { @@ -261,7 +280,7 @@ class SysModModel:public SysModule { uint8_t getValueRowNr = UINT8_MAX; int varCounter = 1; //start with 1 so it can be negative, see var["o"] - std::vector varFunctions; + std::vector varEvents; SysModModel(); void setup(); @@ -310,21 +329,21 @@ class SysModModel:public SysModule { bool changed = false; if (rowNr == UINT8_MAX) { //normal situation - if (var["value"].isNull() || var["value"].as() != value) { //const char * will be JsonString so comparison works - if (!var["value"].isNull() && !variable.readOnly()) var["oldValue"] = var["value"]; + if (variable.value().isNull() || variable.value().as() != value) { //const char * will be JsonString so comparison works + if (!variable.value().isNull() && !variable.readOnly()) var["oldValue"] = variable.value(); var["value"] = value; //trick to remove null values - if (var["value"].isNull() || var["value"].as() == UINT16_MAX) { + if (variable.value().isNull() || variable.value().as() == UINT16_MAX) { var.remove("value"); - // ppf("dev setValue value removed %s %s\n", Variable(var).id(), var["oldValue"].as().c_str()); + // ppf("dev setValue value removed %s %s\n", variable.id(), var["oldValue"].as().c_str()); } else { //only print if ! read only // if (!variable.readOnly()) // ppf("setValue changed %s.%s %s -> %s\n", variable.pid(), variable.id(), var["oldValue"].as().c_str(), variable.valueString().c_str()); // else - // ppf("setValue changed %s %s\n", Variable(var).id(), var["value"].as().c_str()); - web->addResponse(var, "value", var["value"]); + // ppf("setValue changed %s %s\n", variable.id(), variable.value().as().c_str()); + web->addResponse(variable.var, "value", variable.value()); changed = true; } } @@ -332,12 +351,12 @@ class SysModModel:public SysModule { else { //if we deal with multiple rows, value should be an array, if not we create one - if (var["value"].isNull() || !var["value"].is()) { - // ppf("setValue var %s[%d] value %s not array, creating\n", Variable(var).id(), rowNr, var["value"].as().c_str()); + if (variable.value().isNull() || !variable.value().is()) { + // ppf("setValue var %s[%d] value %s not array, creating\n", variable.id(), rowNr, variable.value().as().c_str()); var["value"].to(); } - if (var["value"].is()) { + if (variable.value().is()) { JsonArray valueArray = variable.valArray(); //set the right value in the array (if array did not contain values yet, all values before rownr are set to false) bool notSame = true; //rowNr >= size @@ -350,7 +369,7 @@ class SysModModel:public SysModule { // ppf("notSame %d %d\n", rowNr, valueArray.size()); valueArray[rowNr] = value; //if valueArray[().c_str()); - web->addResponse(var, "value", var["value"]); //send the whole array to UI as response is in format value: !! + web->addResponse(variable.var, "value", variable.value()); //send the whole array to UI as response is in format value: !! changed = true; } } @@ -389,7 +408,7 @@ class SysModModel:public SysModule { } JsonVariant getValue(JsonObject var, uint8_t rowNr = UINT8_MAX) { Variable variable = Variable(var); - if (var["value"].is()) { + if (variable.value().is()) { JsonArray valueArray = variable.valArray(); if (rowNr == UINT8_MAX) rowNr = getValueRowNr; if (rowNr != UINT8_MAX && rowNr < valueArray.size()) @@ -402,7 +421,7 @@ class SysModModel:public SysModule { } } else - return var["value"]; + return variable.value(); } //returns the var defined by id (parent to recursively call findVar) diff --git a/src/Sys/SysModNetwork.cpp b/src/Sys/SysModNetwork.cpp index 2783ec2..3423739 100644 --- a/src/Sys/SysModNetwork.cpp +++ b/src/Sys/SysModNetwork.cpp @@ -31,15 +31,15 @@ void SysModNetwork::setup() { parentVar = ui->initSysMod(parentVar, name, 3502); parentVar["s"] = true; //setup - // JsonObject tableVar = ui->initTable(parentVar, "wfTbl", nullptr, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { //varFun ro false: create and delete row possible - // ui->setComment(var, "List of defined and available Wifi APs"); + // JsonObject tableVar = ui->initTable(parentVar, "wfTbl", nullptr, false, [this](EventArguments) { //varEvent ro false: create and delete row possible + // variable.setComment("List of defined and available Wifi APs"); // }); JsonObject currentVar; - currentVar = ui->initCheckBox(parentVar, "wiFi", true, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + currentVar = ui->initCheckBox(parentVar, "wiFi", true, false, [this](EventArguments) { switch (eventType) { case onChange: - if (var["value"].as()) + if (variable.value().as()) initWiFiConnection(); else stopWiFiConnection(); @@ -47,7 +47,7 @@ void SysModNetwork::setup() { default: return false; }}); - ui->initText(currentVar, "ssid", "", 31, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(currentVar, "ssid", "", 31, false, [this](EventArguments) { switch (eventType) { case onChange: if (mdl->getValue("Network", "wiFi").as()) { stopWiFiConnection(); @@ -57,7 +57,7 @@ void SysModNetwork::setup() { default: return false; }}); - ui->initPassword(currentVar, "password", "", 63, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPassword(currentVar, "password", "", 63, false, [this](EventArguments) { switch (eventType) { case onChange: if (mdl->getValue("Network", "wiFi").as()) { stopWiFiConnection(); @@ -67,70 +67,70 @@ void SysModNetwork::setup() { default: return false; }}); - ui->initText(currentVar, "rssi", nullptr, 32, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(currentVar, "rssi", nullptr, 32, true, [](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%d dBm", WiFi.RSSI(), 0); //0 is to force format overload used + mdl->setValue(variable.var, "%d dBm", WiFi.RSSI(), 0); //0 is to force format overload used return true; default: return false; }}); - ui->initText(currentVar, "status", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(currentVar, "status", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%s %s (s:%d)", wfActive?WiFi.localIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", wfActive?WiFi.localIP().toString().c_str():"inactive", WiFi.status()); + mdl->setValue(variable.var, "%s %s (s:%d)", wfActive?WiFi.localIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", wfActive?WiFi.localIP().toString().c_str():"inactive", WiFi.status()); return true; default: return false; }}); #ifdef STARBASE_ETHERNET - currentVar = ui->initCheckBox(parentVar, "ethernet", false, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + currentVar = ui->initCheckBox(parentVar, "ethernet", false, false, [this](EventArguments) { switch (eventType) { case onLoop1s: //initEthernet not done in onChange as initEthernet needs a bit of a delay - if (!ethActive && mdl->getValue(var).as()) + if (!ethActive && mdl->getValue(variable.var).as()) initEthernet(); default: return false; }}); //set olimex default as details hidden then - ui->initSelect(currentVar, "config", 1, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(currentVar, "config", 1, false, [this](EventArguments) { switch (eventType) { case onUI: { - JsonArray options = ui->setOptions(var); + JsonArray options = variable.setOptions(); options.add("Manual"); options.add("Olimex ESP32 Gateway"); return true; } case onChange: - Variable(var).preDetails(); + variable.preDetails(); mdl->setValueRowNr = rowNr; - if (var["value"] == 0) {//manual - ui->initNumber(var, "address", (uint16_t)0, 0, 255, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + if (variable.value() == 0) {//manual + ui->initNumber(variable.var, "address", (uint16_t)0, 0, 255, false, [this](EventArguments) { switch (eventType) { case onChange: ethActive = false; return true; default: return false; }}); - ui->initPin(var, "power", 14, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPin(variable.var, "power", 14, false, [this](EventArguments) { switch (eventType) { case onChange: ethActive = false; return true; default: return false; }}); - ui->initPin(var, "mdc", 23, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPin(variable.var, "mdc", 23, false, [this](EventArguments) { switch (eventType) { case onChange: ethActive = false; return true; default: return false; }}); - ui->initPin(var, "mdio", 18, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPin(variable.var, "mdio", 18, false, [this](EventArguments) { switch (eventType) { case onChange: ethActive = false; return true; default: return false; }}); - ui->initSelect(var, "type", ETH_PHY_LAN8720, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(variable.var, "type", ETH_PHY_LAN8720, false, [this](EventArguments) { switch (eventType) { case onUI: { - JsonArray options = ui->setOptions(var); + JsonArray options = variable.setOptions(); options.add("LAN8720"); options.add("TLK110"); options.add("RTL8201"); @@ -146,9 +146,9 @@ void SysModNetwork::setup() { return true; default: return false; }}); - ui->initSelect(var, "clockMode", ETH_CLOCK_GPIO17_OUT, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(variable.var, "clockMode", ETH_CLOCK_GPIO17_OUT, false, [this](EventArguments) { switch (eventType) { case onUI: { - JsonArray options = ui->setOptions(var); + JsonArray options = variable.setOptions(); options.add("GPIO0_IN"); options.add("GPIO0_OUT"); options.add("GPIO16_OUT"); @@ -162,7 +162,7 @@ void SysModNetwork::setup() { }}); } - Variable(var).postDetails(rowNr); + variable.postDetails(rowNr); mdl->setValueRowNr = UINT8_MAX; ethActive = false; @@ -172,18 +172,18 @@ void SysModNetwork::setup() { default: return false; }}); - ui->initText(currentVar, "status", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(currentVar, "status", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%s %s", ethActive?ETH.localIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", ethActive?ETH.localIP().toString().c_str():"inactive"); + mdl->setValue(variable.var, "%s %s", ethActive?ETH.localIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", ethActive?ETH.localIP().toString().c_str():"inactive"); return true; default: return false; }}); #endif - currentVar = ui->initCheckBox(parentVar, "AP", false, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + currentVar = ui->initCheckBox(parentVar, "AP", false, false, [this](EventArguments) { switch (eventType) { case onChange: - if (var["value"].as()) + if (variable.value().as()) initAP(); else stopAP(); @@ -196,9 +196,9 @@ void SysModNetwork::setup() { // return true; default: return false; }}); - ui->initText(currentVar, "status", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(currentVar, "status", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%s %s", apActive?WiFi.softAPIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", apActive?WiFi.softAPIP().toString().c_str():"inactive"); + mdl->setValue(variable.var, "%s %s", apActive?WiFi.softAPIP()[0]?"šŸŸ¢":"šŸŸ ":"šŸ›‘", apActive?WiFi.softAPIP().toString().c_str():"inactive"); return true; default: return false; }}); diff --git a/src/Sys/SysModPins.cpp b/src/Sys/SysModPins.cpp index a5938fc..32fd829 100644 --- a/src/Sys/SysModPins.cpp +++ b/src/Sys/SysModPins.cpp @@ -26,50 +26,50 @@ void SysModPins::setup() { parentVar = ui->initSysMod(parentVar, name, 2202); //show table of allocated pins - JsonObject tableVar = ui->initTable(parentVar, "pins", nullptr, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = ui->initTable(parentVar, "pins", nullptr, true, [](EventArguments) { switch (eventType) { case onUI: { - ui->setComment(var, "Allocated Pins"); + variable.setComment("Allocated Pins"); return true; } default: return false; }}); - ui->initPin(tableVar, "pin", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initPin(tableVar, "pin", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var.remove("value"); - ppf("pin onSetValue %s %d\n", var["value"].as().c_str(), getNrOfAllocatedPins()); + variable.var.remove("value"); + ppf("pin onSetValue %s %d\n", variable.valueString().c_str(), getNrOfAllocatedPins()); for (uint8_t rowNr = 0; rowNr < getNrOfAllocatedPins(); rowNr++) - mdl->setValue(var, getPinNr(rowNr), rowNr); + mdl->setValue(variable.var, getPinNr(rowNr), rowNr); return true; default: return false; }}); - ui->initText(tableVar, "owner", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "owner", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var.remove("value"); + variable.var.remove("value"); for (uint8_t rowNr = 0; rowNr < getNrOfAllocatedPins(); rowNr++) - mdl->setValue(var, JsonString(getNthAllocatedPinObject(rowNr).owner, JsonString::Copied), rowNr); + mdl->setValue(variable.var, JsonString(getNthAllocatedPinObject(rowNr).owner, JsonString::Copied), rowNr); return true; default: return false; }}); - ui->initText(tableVar, "details", nullptr, 256, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "details", nullptr, 256, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var.remove("value"); + variable.var.remove("value"); for (uint8_t rowNr = 0; rowNr < getNrOfAllocatedPins(); rowNr++) { // ppf("details[%d] d:%s\n", rowNr, getNthAllocatedPinObject(rowNr).details); - mdl->setValue(var, JsonString(getNthAllocatedPinObject(rowNr).details, JsonString::Copied), rowNr); + mdl->setValue(variable.var, JsonString(getNthAllocatedPinObject(rowNr).details, JsonString::Copied), rowNr); } return true; default: return false; }}); - ui->initCanvas(parentVar, "board", UINT16_MAX, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCanvas(parentVar, "board", UINT16_MAX, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Pin viewer šŸš§"); + variable.setComment("Pin viewer šŸš§"); return true; case onLoop: if (!web->isBusy && web->ws.getClients().length()) { - var["interval"] = 100; //every 100 ms + variable.var["interval"] = 100; //every 100 ms size_t len = NUM_DIGITAL_PINS + 5; AsyncWebSocketMessageBuffer *wsBuf= web->ws.makeBuffer(len); //global wsBuf causes crash in audio sync module!!! @@ -102,14 +102,14 @@ void SysModPins::setup() { allocatePin(19, "Pins", "Relais"); pinMode(19, OUTPUT); //tbd: part of allocatePin? - ui->initCheckBox(parentVar, "pin19", true, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(parentVar, "pin19", true, false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "šŸš§ used for relais on Serg shields"); + variable.setComment("šŸš§ used for relais on Serg shields"); return true; case onChange: { - bool pinValue = var["value"]; + bool pinValue = variable.value(); - ppf("onChange pin19 %s:=%d\n", Variable(var).id(), pinValue); + ppf("onChange pin19 %s.%s:=%d\n", variable.pid(), variable.id(), pinValue); // softhack007: writing these pins on S3/C3/S2 may cause major problems (crashes included) digitalWrite(19, pinValue?HIGH:LOW); diff --git a/src/Sys/SysModPrint.cpp b/src/Sys/SysModPrint.cpp index cf91473..367c219 100644 --- a/src/Sys/SysModPrint.cpp +++ b/src/Sys/SysModPrint.cpp @@ -57,10 +57,10 @@ void SysModPrint::setup() { parentVar = ui->initSysMod(parentVar, name, 2302); //default to Serial - ui->initSelect(parentVar, "output", 1, false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(parentVar, "output", 1, false, [](EventArguments) { switch (eventType) { case onUI: { - JsonArray options = ui->setOptions(var); + JsonArray options = variable.setOptions(); options.add("No"); options.add("Serial"); options.add("UI"); @@ -85,7 +85,7 @@ void SysModPrint::printf(const char * format, ...) { uint8_t output = 1; //default serial char buffer[512]; //this is a lot for the stack - move to heap? - vsnprintf(buffer, sizeof(buffer)-1, format, args); + vsnprintf(buffer, sizeof(buffer), format, args); bool toSerial = false; if (mdls->isConnected) { @@ -101,8 +101,8 @@ void SysModPrint::printf(const char * format, ...) { responseObject["Print.log"]["value"] = buffer; else responseObject["Print.log"]["value"] = responseObject["Print.log"]["value"].as() + String(buffer); - // web->addResponse(var, "value", JsonString(buffer, JsonString::Copied)); //setValue not necessary - // mdl->setValue(var, "%s", buffer); + // web->addResponse(variable.var, "value", JsonString(buffer, JsonString::Copied)); //setValue not necessary + // mdl->setValue(variable.var, "%s", buffer); } else if (output == 3) { //tbd diff --git a/src/Sys/SysModSystem.cpp b/src/Sys/SysModSystem.cpp index ca1c994..12b1332 100644 --- a/src/Sys/SysModSystem.cpp +++ b/src/Sys/SysModSystem.cpp @@ -41,51 +41,51 @@ void SysModSystem::setup() { parentVar = ui->initSysMod(parentVar, name, 2000); parentVar["s"] = true; //setup - ui->initText(parentVar, "name", _INIT(TOSTRING(APP)), 24, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "name", _INIT(TOSTRING(APP)), 24, false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Instance name"); + variable.setComment("Instance name"); return true; case onChange: char name[24]; - removeInvalidCharacters(name, var["value"]); + removeInvalidCharacters(name, variable.value()); ppf("instance name stripped %s\n", name); - mdl->setValue(var, JsonString(name, JsonString::Copied)); //update with stripped name + mdl->setValue(variable.var, JsonString(name, JsonString::Copied)); //update with stripped name mdns->resetMDNS(); // set the new name for mdns return true; default: return false; }}); - ui->initText(parentVar, "uptime", nullptr, 16, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "uptime", nullptr, 16, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "s. Uptime of board"); + variable.setComment("s. Uptime of board"); return true; case onLoop1s: - mdl->setValue(var, millis()/1000); + mdl->setValue(variable.var, millis()/1000); return true; default: return false; }}); - ui->initNumber(parentVar, "now", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(parentVar, "now", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "s"); + variable.setComment("s"); return true; case onLoop1s: - mdl->setValue(var, now/1000); + mdl->setValue(variable.var, now/1000); return true; default: return false; }}); - ui->initNumber(parentVar, "timeBase", UINT16_MAX, 0, (unsigned long)-1, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(parentVar, "timeBase", UINT16_MAX, 0, (unsigned long)-1, true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "s"); + variable.setComment("s"); return true; case onLoop1s: - mdl->setValue(var, (nowsetValue(variable.var, (nowinitButton(parentVar, "reboot", false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initButton(parentVar, "reboot", false, [](EventArguments) { switch (eventType) { case onChange: web->ws.closeAll(1012); @@ -100,12 +100,12 @@ void SysModSystem::setup() { default: return false; }}); - ui->initText(parentVar, "loops", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "loops", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Loops per second"); + variable.setComment("Loops per second"); return true; case onLoop1s: - mdl->setValue(var, loopCounter); + mdl->setValue(variable.var, loopCounter); loopCounter = 0; return true; default: return false; @@ -114,73 +114,73 @@ void SysModSystem::setup() { print->fFormat(chipInfo, sizeof(chipInfo), "%s %s (%d.%d.%d) c#:%d %d mHz f:%d KB %d mHz %d", ESP.getChipModel(), ESP.getSdkVersion(), ESP_ARDUINO_VERSION_MAJOR, ESP_ARDUINO_VERSION_MINOR, ESP_ARDUINO_VERSION_PATCH, ESP.getChipCores(), ESP.getCpuFreqMHz(), ESP.getFlashChipSize()/1024, ESP.getFlashChipSpeed()/1000000, ESP.getFlashChipMode()); ui->initText(parentVar, "chip", chipInfo, 16, true); - ui->initProgress(parentVar, "heap", 0, 0, ESP.getHeapSize()/1000, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initProgress(parentVar, "heap", 0, 0, ESP.getHeapSize()/1000, true, [](EventArguments) { switch (eventType) { case onChange: - var["max"] = ESP.getHeapSize()/1000; //makes sense? - web->addResponse(var, "comment", "f:%d / t:%d (l:%d) B [%d %d]", ESP.getFreeHeap(), ESP.getHeapSize(), ESP.getMaxAllocHeap(), esp_get_free_heap_size(), esp_get_free_internal_heap_size()); + variable.var["max"] = ESP.getHeapSize()/1000; //makes sense? + web->addResponse(variable.var, "comment", "f:%d / t:%d (l:%d) B [%d %d]", ESP.getFreeHeap(), ESP.getHeapSize(), ESP.getMaxAllocHeap(), esp_get_free_heap_size(), esp_get_free_internal_heap_size()); //temporary add esp_get_free_heap_size(), esp_get_free_internal_heap_size() to see if/how it differs return true; case onLoop1s: - mdl->setValue(var, (ESP.getHeapSize()-ESP.getFreeHeap()) / 1000); + mdl->setValue(variable.var, (ESP.getHeapSize()-ESP.getFreeHeap()) / 1000); return true; default: return false; }}); if (psramFound()) { - ui->initProgress(parentVar, "psram", 0, 0, ESP.getPsramSize()/1000, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initProgress(parentVar, "psram", 0, 0, ESP.getPsramSize()/1000, true, [](EventArguments) { switch (eventType) { case onChange: - var["max"] = ESP.getPsramSize()/1000; //makes sense? - web->addResponse(var, "comment", "%d / %d (%d) B", ESP.getFreePsram(), ESP.getPsramSize(), ESP.getMinFreePsram()); + variable.var["max"] = ESP.getPsramSize()/1000; //makes sense? + web->addResponse(variable.var, "comment", "%d / %d (%d) B", ESP.getFreePsram(), ESP.getPsramSize(), ESP.getMinFreePsram()); return true; case onLoop1s: - mdl->setValue(var, (ESP.getPsramSize()-ESP.getFreePsram()) / 1000); + mdl->setValue(variable.var, (ESP.getPsramSize()-ESP.getFreePsram()) / 1000); return true; default: return false; }}); } - ui->initProgress(parentVar, "mainStack", 0, 0, getArduinoLoopTaskStackSize(), true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initProgress(parentVar, "mainStack", 0, 0, getArduinoLoopTaskStackSize(), true, [this](EventArguments) { switch (eventType) { case onChange: - var["max"] = getArduinoLoopTaskStackSize(); //makes sense? - web->addResponse(var, "comment", "%d of %d B", sysTools_get_arduino_maxStackUsage(), getArduinoLoopTaskStackSize()); + variable.var["max"] = getArduinoLoopTaskStackSize(); //makes sense? + web->addResponse(variable.var, "comment", "%d of %d B", sysTools_get_arduino_maxStackUsage(), getArduinoLoopTaskStackSize()); return true; case onLoop1s: - mdl->setValue(var, sysTools_get_arduino_maxStackUsage()); + mdl->setValue(variable.var, sysTools_get_arduino_maxStackUsage()); return true; default: return false; }}); - ui->initProgress(parentVar, "TCPStack", 0, 0, CONFIG_ASYNC_TCP_STACK_SIZE, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initProgress(parentVar, "TCPStack", 0, 0, CONFIG_ASYNC_TCP_STACK_SIZE, true, [this](EventArguments) { switch (eventType) { case onChange: - web->addResponse(var, "comment", "%d of %d B", sysTools_get_webserver_maxStackUsage(), CONFIG_ASYNC_TCP_STACK_SIZE); + web->addResponse(variable.var, "comment", "%d of %d B", sysTools_get_webserver_maxStackUsage(), CONFIG_ASYNC_TCP_STACK_SIZE); return true; case onLoop1s: - mdl->setValue(var, sysTools_get_webserver_maxStackUsage()); + mdl->setValue(variable.var, sysTools_get_webserver_maxStackUsage()); return true; default: return false; }}); - ui->initSelect(parentVar, "reset 0", (int)rtc_get_reset_reason(0), true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(parentVar, "reset 0", (int)rtc_get_reset_reason(0), true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Reason Core 0"); - addResetReasonsSelect(ui->setOptions(var)); + variable.setComment("Reason Core 0"); + addResetReasonsSelect(variable.setOptions()); return true; default: return false; }}); if (ESP.getChipCores() > 1) - ui->initSelect(parentVar, "reset 1", (int)rtc_get_reset_reason(1), true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(parentVar, "reset 1", (int)rtc_get_reset_reason(1), true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Reason Core 1"); - addResetReasonsSelect(ui->setOptions(var)); + variable.setComment("Reason Core 1"); + addResetReasonsSelect(variable.setOptions()); return true; default: return false; }}); - ui->initSelect(parentVar, "restart", (int)esp_reset_reason(), true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(parentVar, "restart", (int)esp_reset_reason(), true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Restart reason"); - addRestartReasonsSelect(ui->setOptions(var)); + variable.setComment("Restart reason"); + addRestartReasonsSelect(variable.setOptions()); return true; default: return false; }}); @@ -206,9 +206,9 @@ void SysModSystem::setup() { // ui->initText(parentVar, "date", __DATE__, 16, true); // ui->initText(parentVar, "time", __TIME__, 16, true); - ui->initFileUpload(parentVar, "update", nullptr, UINT16_MAX, false, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initFileUpload(parentVar, "update", nullptr, UINT16_MAX, false, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "OTA Firmware Update"); + variable.setComment("OTA Firmware Update"); return true; default: return false; }}); diff --git a/src/Sys/SysModUI.cpp b/src/Sys/SysModUI.cpp index 88dce18..5e9a461 100644 --- a/src/Sys/SysModUI.cpp +++ b/src/Sys/SysModUI.cpp @@ -22,28 +22,28 @@ void SysModUI::setup() { parentVar = initSysMod(parentVar, name, 4101); - JsonObject tableVar = initTable(parentVar, "loops", nullptr, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = initTable(parentVar, "loops", nullptr, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Loops initiated by a variable"); + variable.setComment("Loops initiated by a variable"); return true; default: return false; }}); - initText(tableVar, "variable", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + initText(tableVar, "variable", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < loopFunctions.size(); rowNr++) - mdl->setValue(var, JsonString(loopFunctions[rowNr].var["id"], JsonString::Copied), rowNr); + mdl->setValue(variable.var, JsonString(loopFunctions[rowNr].var["id"], JsonString::Copied), rowNr); return true; default: return false; }}); - initNumber(tableVar, "#loops", UINT16_MAX, 0, 999, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + initNumber(tableVar, "#loops", UINT16_MAX, 0, 999, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < loopFunctions.size(); rowNr++) - mdl->setValue(var, loopFunctions[rowNr].counter, rowNr); + mdl->setValue(variable.var, loopFunctions[rowNr].counter, rowNr); return true; case onLoop1s: - Variable(var).triggerEvent(onSetValue); //set the value (WIP) + variable.triggerEvent(onSetValue); //set the value (WIP) for (VarLoop &varLoop : loopFunctions) varLoop.counter = 0; return true; @@ -65,7 +65,7 @@ void SysModUI::loop20ms() { //never more then 50 times a second! } } -JsonObject SysModUI::initVar(JsonObject parent, const char * id, const char * type, bool readOnly, VarFun varFun) { +JsonObject SysModUI::initVar(JsonObject parent, const char * id, const char * type, bool readOnly, VarEvent varEvent) { const char * parentId = parent["id"]; if (!parentId) parentId = "m"; //m=module JsonObject var = mdl->findVar(parentId, id); @@ -109,24 +109,24 @@ JsonObject SysModUI::initVar(JsonObject parent, const char * id, const char * ty variable.order( -mdl->varCounter++); //redefine order } - //if varFun, add it to the list - if (varFun) { + //if varEvent, add it to the list + if (varEvent) { //if fun already in ucFunctions then reuse, otherwise add new fun in ucFunctions //lambda update: when replacing typedef void(*UCFun)(JsonObject); with typedef std::function UCFun; this gives error: // mismatched types 'T*' and 'std::function' { return *__it == _M_value; } // it also looks like functions are not added more then once anyway - // std::vector::iterator itr = find(ucFunctions.begin(), ucFunctions.end(), varFun); + // std::vector::iterator itr = find(ucFunctions.begin(), ucFunctions.end(), varEvent); // if (itr!=ucFunctions.end()) //found - // var["varFun"] = distance(ucFunctions.begin(), itr); //assign found function + // var["varEvent"] = distance(ucFunctions.begin(), itr); //assign found function // else { //not found - mdl->varFunctions.push_back(varFun); //add new function - var["fun"] = mdl->varFunctions.size()-1; + mdl->varEvents.push_back(varEvent); //add new function + var["fun"] = mdl->varEvents.size()-1; // } - if (varFun(var, UINT8_MAX, onLoop)) { //test run if it supports loop + if (varEvent(var, UINT8_MAX, onLoop)) { //test run if it supports loop //no need to check if already in... VarLoop loop; - loop.loopFun = varFun; + loop.loopFun = varEvent; loop.var = var; loopFunctions.push_back(loop); @@ -144,7 +144,7 @@ JsonObject SysModUI::initVar(JsonObject parent, const char * id, const char * ty void SysModUI::processJson(JsonVariant json) { if (json.is()) //should be { - //varFun adds object elements to json which would be processed in the for loop. So we freeze the original pairs in a vector and loop on this + //varEvent adds object elements to json which would be processed in the for loop. So we freeze the original pairs in a vector and loop on this std::vector pairs; for (JsonPair pair : json.as()) { //iterate json elements pairs.push_back(pair); diff --git a/src/Sys/SysModUI.h b/src/Sys/SysModUI.h index 463da70..01ac694 100644 --- a/src/Sys/SysModUI.h +++ b/src/Sys/SysModUI.h @@ -16,7 +16,7 @@ struct VarLoop { JsonObject var; - VarFun loopFun; + VarEvent loopFun; unsigned long lastMillis = 0; unsigned long counter = 0; }; @@ -49,122 +49,126 @@ class SysModUI: public SysModule { return var; } - JsonObject initTable(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "table", value, 0, 0, readOnly, varFun); + JsonObject initTable(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "table", value, 0, 0, readOnly, varEvent); } - JsonObject initText(JsonObject parent, const char * id, const char * value = nullptr, uint16_t max = 32, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "text", value, 0, max, readOnly, varFun); + JsonObject initText(JsonObject parent, const char * id, const char * value = nullptr, uint16_t max = 32, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "text", value, 0, max, readOnly, varEvent); } //vector of text - JsonObject initTextVector(JsonObject parent, const char * id, std::vector *values, uint16_t max = 32, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValueVector(parent, id, "text", values, 0, max, readOnly, varFun); + JsonObject initTextVector(JsonObject parent, const char * id, std::vector *values, uint16_t max = 32, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValueVector(parent, id, "text", values, 0, max, readOnly, varEvent); } - JsonObject initFileUpload(JsonObject parent, const char * id, const char * value = nullptr, uint16_t max = 32, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "fileUpload", value, 0, max, readOnly, varFun); + JsonObject initFileUpload(JsonObject parent, const char * id, const char * value = nullptr, uint16_t max = 32, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "fileUpload", value, 0, max, readOnly, varEvent); } - JsonObject initPassword(JsonObject parent, const char * id, const char * value = nullptr, uint8_t max = 32, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "password", value, 0, max, readOnly, varFun); + JsonObject initPassword(JsonObject parent, const char * id, const char * value = nullptr, uint8_t max = 32, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "password", value, 0, max, readOnly, varEvent); } //number is uint16_t for the time being (because it is called by uint16_t referenced vars...) - JsonObject initNumber(JsonObject parent, const char * id, uint16_t value = UINT16_MAX, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "number", value, min, max, readOnly, varFun); + JsonObject initNumber(JsonObject parent, const char * id, uint16_t value = UINT16_MAX, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "number", value, min, max, readOnly, varEvent); } //init a number using referenced value - JsonObject initNumber(JsonObject parent, const char * id, uint16_t * value = nullptr, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "number", value, min, max, readOnly, varFun); + JsonObject initNumber(JsonObject parent, const char * id, uint16_t * value = nullptr, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "number", value, min, max, readOnly, varEvent); } //init a number using a vector of integers - JsonObject initNumber(JsonObject parent, const char * id, std::vector *values, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "number", values, min, max, readOnly, varFun); + JsonObject initNumber(JsonObject parent, const char * id, std::vector *values, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "number", values, min, max, readOnly, varEvent); } - JsonObject initPin(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "pin", value, 0, NUM_DIGITAL_PINS, readOnly, varFun); + JsonObject initPin(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "pin", value, 0, NUM_DIGITAL_PINS, readOnly, varEvent); } //referenced value - JsonObject initPin(JsonObject parent, const char * id, uint8_t *value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "pin", value, 0, NUM_DIGITAL_PINS, readOnly, varFun); + JsonObject initPin(JsonObject parent, const char * id, uint8_t *value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "pin", value, 0, NUM_DIGITAL_PINS, readOnly, varEvent); } //type int! - JsonObject initProgress(JsonObject parent, const char * id, int value = UINT16_MAX, int min = 0, int max = 255, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "progress", value, min, max, readOnly, varFun); + JsonObject initProgress(JsonObject parent, const char * id, int value = UINT16_MAX, int min = 0, int max = 255, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "progress", value, min, max, readOnly, varEvent); } - JsonObject initCoord3D(JsonObject parent, const char * id, Coord3D value = {UINT16_MAX, UINT16_MAX, UINT16_MAX}, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "coord3D", value, min, max, readOnly, varFun); + JsonObject initCoord3D(JsonObject parent, const char * id, Coord3D value = {UINT16_MAX, UINT16_MAX, UINT16_MAX}, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "coord3D", value, min, max, readOnly, varEvent); } //init a Coord3D using referenced value - JsonObject initCoord3D(JsonObject parent, const char * id, Coord3D *value = nullptr, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "coord3D", value, min, max, readOnly, varFun); + JsonObject initCoord3D(JsonObject parent, const char * id, Coord3D *value = nullptr, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "coord3D", value, min, max, readOnly, varEvent); } //init a range slider, range between 0 and 255! - JsonObject initSlider(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, int min = 0, int max = 255, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "range", value, min, max, readOnly, varFun); + JsonObject initSlider(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, int min = 0, int max = 255, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "range", value, min, max, readOnly, varEvent); } //init a range slider using referenced value - JsonObject initSlider(JsonObject parent, const char * id, uint8_t * value = nullptr, int min = 0, int max = 255, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "range", value, min, max, readOnly, varFun); + JsonObject initSlider(JsonObject parent, const char * id, uint8_t * value = nullptr, int min = 0, int max = 255, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "range", value, min, max, readOnly, varEvent); } - JsonObject initCanvas(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "canvas", value, 0, 0, readOnly, varFun); + JsonObject initCanvas(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "canvas", value, 0, 0, readOnly, varEvent); } //supports 3 state value: if UINT8_MAX it is indeterminated - JsonObject initCheckBox(JsonObject parent, const char * id, bool3State value = UINT8_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "checkbox", value, 0, 0, readOnly, varFun); + JsonObject initCheckBox(JsonObject parent, const char * id, bool3State value = UINT8_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "checkbox", value, 0, 0, readOnly, varEvent); } //init a checkbox using referenced value - JsonObject initCheckBox(JsonObject parent, const char * id, bool3State *value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "checkbox", value, 0, 0, readOnly, varFun); + JsonObject initCheckBox(JsonObject parent, const char * id, bool3State *value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "checkbox", value, 0, 0, readOnly, varEvent); } //a button never gets a value - JsonObject initButton(JsonObject parent, const char * id, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "button", false, 0, 0, readOnly, varFun); + JsonObject initButton(JsonObject parent, const char * id, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "button", false, 0, 0, readOnly, varEvent); } + // JsonObject initButton2(JsonObject parent, const char * id, bool readOnly = false, VarEvent varEvent = nullptr) { + // // return initVarAndValue(parent, id, "button", false, 0, 0, readOnly, varEvent); + // return JsonObject(); + // } //int value ? - JsonObject initSelect(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "select", value, 0, 0, readOnly, varFun); + JsonObject initSelect(JsonObject parent, const char * id, uint8_t value = UINT8_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "select", value, 0, 0, readOnly, varEvent); } //init a select using referenced value - JsonObject initSelect(JsonObject parent, const char * id, uint8_t * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "select", value, 0, 0, readOnly, varFun); + JsonObject initSelect(JsonObject parent, const char * id, uint8_t * value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "select", value, 0, 0, readOnly, varEvent); } - JsonObject initIP(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "ip", value, 0, 255, readOnly, varFun); + JsonObject initIP(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "ip", value, 0, 255, readOnly, varEvent); } - JsonObject initTextArea(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "textarea", value, 0, 0, readOnly, varFun); + JsonObject initTextArea(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "textarea", value, 0, 0, readOnly, varEvent); } - JsonObject initFileEdit(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "fileEdit", value, 0, 0, readOnly, varFun); + JsonObject initFileEdit(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "fileEdit", value, 0, 0, readOnly, varEvent); } //vector of fileEdit - JsonObject initFileEditVector(JsonObject parent, const char * id, std::vector *values, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValueVector(parent, id, "fileEdit", values, 0, 0, readOnly, varFun); + JsonObject initFileEditVector(JsonObject parent, const char * id, std::vector *values, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValueVector(parent, id, "fileEdit", values, 0, 0, readOnly, varEvent); } - JsonObject initURL(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) { - return initVarAndValue(parent, id, "url", value, 0, 0, readOnly, varFun); + JsonObject initURL(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarEvent varEvent = nullptr) { + return initVarAndValue(parent, id, "url", value, 0, 0, readOnly, varEvent); } //initVarAndValue using basic value template - JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, Type value, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr) { - JsonObject var = initVar(parent, id, type, readOnly, varFun); + JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, Type value, int min = 0, int max = 255, bool readOnly = true, VarEvent varEvent = nullptr) { + JsonObject var = initVar(parent, id, type, readOnly, varEvent); if (initValue(var, min, max, 0)) { //no pointer mdl->setValue(var, value, mdl->setValueRowNr); //does onChange if needed, if var in table, update the table row @@ -175,8 +179,8 @@ class SysModUI: public SysModule { //initVarAndValue using referenced value template - JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, Type * value, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr) { - JsonObject var = initVar(parent, id, type, readOnly, varFun); + JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, Type * value, int min = 0, int max = 255, bool readOnly = true, VarEvent varEvent = nullptr) { + JsonObject var = initVar(parent, id, type, readOnly, varEvent); if (initValue(var, min, max, int(value))) { mdl->setValue(var, *value, mdl->setValueRowNr); //does onChange if needed, if var in table, update the table row @@ -187,8 +191,8 @@ class SysModUI: public SysModule { //initVarAndValue using vector of values template - JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, std::vector *values, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr) { - JsonObject var = initVar(parent, id, type, readOnly, varFun); + JsonObject initVarAndValue(JsonObject parent, const char * id, const char * type, std::vector *values, int min = 0, int max = 255, bool readOnly = true, VarEvent varEvent = nullptr) { + JsonObject var = initVar(parent, id, type, readOnly, varEvent); if (!var["value"].isNull()) { print->printJson("Clearing the vector", var); @@ -207,8 +211,8 @@ class SysModUI: public SysModule { } //initVarAndValue using vector of values . WIP!!! - JsonObject initVarAndValueVector(JsonObject parent, const char * id, const char * type, std::vector *values, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr) { - JsonObject var = initVar(parent, id, type, readOnly, varFun); + JsonObject initVarAndValueVector(JsonObject parent, const char * id, const char * type, std::vector *values, int min = 0, int max = 255, bool readOnly = true, VarEvent varEvent = nullptr) { + JsonObject var = initVar(parent, id, type, readOnly, varEvent); if (!var["value"].isNull()) { print->printJson("Clearing the vector", var); @@ -227,7 +231,7 @@ class SysModUI: public SysModule { } //adds a variable to the model - JsonObject initVar(JsonObject parent, const char * id, const char * type, bool readOnly = true, VarFun varFun = nullptr); + JsonObject initVar(JsonObject parent, const char * id, const char * type, bool readOnly = true, VarEvent varEvent = nullptr); //gives a variable an initital value returns true if setValue must be called bool initValue(JsonObject var, int min = 0, int max = 255, int pointer = 0) { @@ -249,7 +253,7 @@ class SysModUI: public SysModule { if (var["type"] != "button") { //button never gets a value if (var["value"].isNull()) { doSetValue = true; - // print->printJson("initValue varFun value is null", var); + // print->printJson("initValue varEvent value is null", var); } else if (var["value"].is()) { JsonArray valueArray = variable.valArray(); if (mdl->setValueRowNr != UINT8_MAX) { // if var in table @@ -261,7 +265,7 @@ class SysModUI: public SysModule { } } - //sets the default values, by varFun if exists, otherwise manually (by returning true) + //sets the default values, by varEvent if exists, otherwise manually (by returning true) if (doSetValue) { bool onSetValueExists = false; if (!var["fun"].isNull()) { @@ -273,7 +277,7 @@ class SysModUI: public SysModule { } else { //do onChange on existing value //no call of onChange for buttons otherwise all buttons will be fired which is highly undesirable - if (var["type"] != "button") { // && !var["fun"].isNull(): also if no varFun to update pointers !isPointer because 0 is also a value then && (!isPointer || value) + if (var["type"] != "button") { // && !var["fun"].isNull(): also if no varEvent to update pointers !isPointer because 0 is also a value then && (!isPointer || value) bool onChangeExists = false; if (var["value"].is()) { //refill the vector @@ -312,72 +316,6 @@ class SysModUI: public SysModule { //called to rebuild selects and tables (tbd: also label and comments is done again, that is not needed) // void processOnUI(const char * id); - void setLabel(JsonObject var, const char * text) { - web->addResponse(var, "label", text); - } - void setComment(JsonObject var, const char * text) { - web->addResponse(var, "comment", text); - } - JsonArray setOptions(JsonObject var) { - JsonObject responseObject = web->getResponseObject(); - char pidid[64]; - print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); - return responseObject[pidid]["options"].to(); - } - //return the options from onUI (don't forget to clear responseObject) - JsonArray getOptions(JsonObject var) { - Variable(var).triggerEvent(onUI); //rebuild options - char pidid[64]; - print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); - return web->getResponseObject()[pidid]["options"]; - } - void clearOptions(JsonObject var) { - char pidid[64]; - print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); - web->getResponseObject()[pidid].remove("options"); - } - - //find options text in a hierarchy of options - void findOptionsText(JsonObject var, uint8_t value, char * groupName, char * optionName) { - uint8_t startValue = 0; - char pidid[64]; - print->fFormat(pidid, sizeof(pidid), "%s.%s", var["pid"].as(), var["id"].as()); - bool optionsExisted = !web->getResponseObject()[pidid]["options"].isNull(); - JsonString groupNameJS; - JsonString optionNameJS; - JsonArray options = getOptions(var); - if (!findOptionsTextRec(options, &startValue, value, &groupNameJS, &optionNameJS)) - ppf("findOptions select option not found %d %s %s\n", value, groupNameJS.isNull()?"X":groupNameJS.c_str(), optionNameJS.isNull()?"X":optionNameJS.c_str()); - strlcpy(groupName, groupNameJS.c_str(), 32); //groupName is char[32] - strlcpy(optionName, optionNameJS.c_str(), 32); //optionName is char[32] - if (!optionsExisted) - clearOptions(var); //if created here then also remove - } - - // (groupName and optionName as pointers? String is already a pointer?) - bool findOptionsTextRec(JsonVariant options, uint8_t * startValue, uint8_t value, JsonString *groupName, JsonString *optionName, JsonString parentGroup = JsonString()) { - if (options.is()) { //array of options - for (JsonVariant option : options.as()) { - if (findOptionsTextRec(option, startValue, value, groupName, optionName, parentGroup)) - return true; - } - } - else if (options.is()) { //group - for (JsonPair pair: options.as()) { - if (findOptionsTextRec(pair.value(), startValue, value, groupName, optionName, parentGroup.isNull()?pair.key():parentGroup)) //send the master level group name only - return true; - } - } else { //individual option - if (*startValue == value) { - *groupName = parentGroup; - *optionName = options.as(); - ppf("Found %d=%d ? %s . %s\n", *startValue, value, (*groupName).isNull()?"":(*groupName).c_str(), (*optionName).isNull()?"":(*optionName).c_str()); - return true; - } - (*startValue)++; - } - return false; - } private: std::vector loopFunctions; diff --git a/src/Sys/SysModWeb.cpp b/src/Sys/SysModWeb.cpp index 82bd729..4410a61 100644 --- a/src/Sys/SysModWeb.cpp +++ b/src/Sys/SysModWeb.cpp @@ -47,47 +47,47 @@ void SysModWeb::setup() { SysModule::setup(); parentVar = ui->initSysMod(parentVar, name, 3101); - JsonObject tableVar = ui->initTable(parentVar, "clients", nullptr, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = ui->initTable(parentVar, "clients", nullptr, true, [](EventArguments) { switch (eventType) { case onLoop1s: - for (JsonObject childVar: Variable(var).children()) + for (JsonObject childVar: variable.children()) Variable(childVar).triggerEvent(onSetValue); //set the value (WIP) default: return false; }}); - ui->initNumber(tableVar, "nr", UINT16_MAX, 0, 999, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "nr", UINT16_MAX, 0, 999, true, [this](EventArguments) { switch (eventType) { case onSetValue: { uint8_t rowNr = 0; for (auto &client:ws.getClients()) - mdl->setValue(var, client->id(), rowNr++); + mdl->setValue(variable.var, client->id(), rowNr++); return true; } default: return false; }}); - ui->initText(tableVar, "ip", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "ip", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onSetValue: { uint8_t rowNr = 0; for (auto &client:ws.getClients()) - mdl->setValue(var, JsonString(client->remoteIP().toString().c_str(), JsonString::Copied), rowNr++); + mdl->setValue(variable.var, JsonString(client->remoteIP().toString().c_str(), JsonString::Copied), rowNr++); return true; } default: return false; }}); //UINT8_MAX: tri state boolean: not true not false - ui->initCheckBox(tableVar, "full", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(tableVar, "full", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: { uint8_t rowNr = 0; for (auto &client:ws.getClients()) - mdl->setValue(var, client->queueIsFull(), rowNr++); + mdl->setValue(variable.var, client->queueIsFull(), rowNr++); return true; } default: return false; }}); - ui->initSelect(tableVar, "status", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(tableVar, "status", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: { uint8_t rowNr = 0; for (auto &client:ws.getClients()) - mdl->setValue(var, client->status(), rowNr++); + mdl->setValue(variable.var, client->status(), rowNr++); return true; } case onUI: { //tbd: not working yet in ui - JsonArray options = ui->setOptions(var); + JsonArray options = variable.setOptions(); options.add("Disconnected"); //0 options.add("Connected"); //1 options.add("Disconnecting"); //2 @@ -96,46 +96,46 @@ void SysModWeb::setup() { default: return false; }}); - ui->initNumber(tableVar, "length", UINT16_MAX, 0, WS_MAX_QUEUED_MESSAGES, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "length", UINT16_MAX, 0, WS_MAX_QUEUED_MESSAGES, true, [this](EventArguments) { switch (eventType) { case onSetValue: { uint8_t rowNr = 0; for (auto &client:ws.getClients()) - mdl->setValue(var, client->queueLen(), rowNr++); + mdl->setValue(variable.var, client->queueLen(), rowNr++); return true; } default: return false; }}); ui->initNumber(parentVar, "maxQueue", WS_MAX_QUEUED_MESSAGES, 0, WS_MAX_QUEUED_MESSAGES, true); - ui->initText(parentVar, "WSSend", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "WSSend", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "#: %d /s T: %d B/s B:%d B/s", sendWsCounter, sendWsTBytes, sendWsBBytes); + mdl->setValue(variable.var, "#: %d /s T: %d B/s B:%d B/s", sendWsCounter, sendWsTBytes, sendWsBBytes); sendWsCounter = 0; sendWsTBytes = 0; sendWsBBytes = 0; default: return false; }}); - ui->initText(parentVar, "WSRecv", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "WSRecv", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "#: %d /s %d B/s", recvWsCounter, recvWsBytes); + mdl->setValue(variable.var, "#: %d /s %d B/s", recvWsCounter, recvWsBytes); recvWsCounter = 0; recvWsBytes = 0; return true; default: return false; }}); - ui->initText(parentVar, "UDPSend", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "UDPSend", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "#: %d /s %d B/s", sendUDPCounter, sendUDPBytes); + mdl->setValue(variable.var, "#: %d /s %d B/s", sendUDPCounter, sendUDPBytes); sendUDPCounter = 0; sendUDPBytes = 0; return true; default: return false; }}); - ui->initText(parentVar, "UDPRecv", nullptr, 16, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "UDPRecv", nullptr, 16, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "#: %d /s %d B/s", recvUDPCounter, recvUDPBytes); + mdl->setValue(variable.var, "#: %d /s %d B/s", recvUDPCounter, recvUDPBytes); recvUDPCounter = 0; recvUDPBytes = 0; default: return false; diff --git a/src/SysModules.cpp b/src/SysModules.cpp index ef72708..2fb335d 100644 --- a/src/SysModules.cpp +++ b/src/SysModules.cpp @@ -26,8 +26,8 @@ void SysModules::setup() { //delete Modules values if nr of modules has changed (new values created using module defaults) for (JsonObject childVar: Variable(mdl->findVar("Modules", "Modules")).children()) { Variable childVariable = Variable(childVar); - if (!childVar["value"].isNull() && childVariable.valArray().size() != modules.size()) { - ppf("Modules clear (%s %s) %d %d\n", childVariable.id(), childVariable.valueString().c_str(), modules.size(), childVariable.valArray().size()); + if (!childVariable.value().isNull() && childVariable.valArray().size() != modules.size()) { + ppf("Modules clear (%s.%s %s) %d %d\n", childVariable.pid(), childVariable.id(), childVariable.valueString().c_str(), modules.size(), childVariable.valArray().size()); childVar.remove("value"); } } @@ -35,41 +35,41 @@ void SysModules::setup() { //do its own setup: will be shown as last module JsonObject parentVar = ui->initSysMod(parentVar, "Modules", 4203); - JsonObject tableVar = ui->initTable(parentVar, "Modules", nullptr, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = ui->initTable(parentVar, "Modules", nullptr, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "List of modules"); + variable.setComment("List of modules"); return true; default: return false; }}); - ui->initText(tableVar, "name", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "name", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < modules.size(); rowNr++) - mdl->setValue(var, JsonString(modules[rowNr]->name, JsonString::Copied), rowNr); + mdl->setValue(variable.var, JsonString(modules[rowNr]->name, JsonString::Copied), rowNr); return true; default: return false; }}); //UINT8_MAX: tri state boolean: not true not false - ui->initCheckBox(tableVar, "success", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(tableVar, "success", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < modules.size(); rowNr++) - mdl->setValue(var, modules[rowNr]->success, rowNr); + mdl->setValue(variable.var, modules[rowNr]->success, rowNr); return true; default: return false; }}); //UINT8_MAX: tri state boolean: not true not false - ui->initCheckBox(tableVar, "enabled", UINT8_MAX, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun not readonly! (tbd) + ui->initCheckBox(tableVar, "enabled", UINT8_MAX, false, [this](EventArguments) { switch (eventType) { //not readonly! (tbd) case onSetValue: //never a rowNr as parameter, set all //execute only if var has not been set for (size_t rowNr = 0; rowNr < modules.size(); rowNr++) - mdl->setValue(var, modules[rowNr]->isEnabled, rowNr); + mdl->setValue(variable.var, modules[rowNr]->isEnabled, rowNr); return true; case onChange: if (rowNr != UINT8_MAX && rowNr < modules.size()) { - modules[rowNr]->isEnabled = mdl->getValue(var, rowNr); + modules[rowNr]->isEnabled = mdl->getValue(variable.var, rowNr); modules[rowNr]->enabledChanged(); } else { diff --git a/src/User/UserModE131.h b/src/User/UserModE131.h index 34eb68e..39ef064 100644 --- a/src/User/UserModE131.h +++ b/src/User/UserModE131.h @@ -29,9 +29,9 @@ class UserModE131:public SysModule { ui->initNumber(parentVar, "universe", &universe, 0, 7); - JsonObject currentVar = ui->initNumber(parentVar, "channel", &channel, 1, 512, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject currentVar = ui->initNumber(parentVar, "channel", &channel, 1, 512, false, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "First channel"); + variable.setComment("First channel"); return true; case onChange: for (JsonObject childVar: Variable(mdl->findVar("E131", "watches")).children()) @@ -41,41 +41,41 @@ class UserModE131:public SysModule { }}); currentVar["dash"] = true; - JsonObject tableVar = ui->initTable(parentVar, "watches", nullptr, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + JsonObject tableVar = ui->initTable(parentVar, "watches", nullptr, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "Variables to watch"); + variable.setComment("Variables to watch"); return true; default: return false; }}); - ui->initNumber(tableVar, "channel", UINT16_MAX, 1, 512, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "channel", UINT16_MAX, 1, 512, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < varsToWatch.size(); rowNr++) - mdl->setValue(var, channel + varsToWatch[rowNr].channelOffset, rowNr); + mdl->setValue(variable.var, channel + varsToWatch[rowNr].channelOffset, rowNr); return true; default: return false; }}); - ui->initText(tableVar, "variable", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "variable", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < varsToWatch.size(); rowNr++) - mdl->setValue(var, varsToWatch[rowNr].id, rowNr); + mdl->setValue(variable.var, varsToWatch[rowNr].id, rowNr); return true; default: return false; }}); - ui->initNumber(tableVar, "max", UINT16_MAX, 0, UINT16_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "max", UINT16_MAX, 0, UINT16_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < varsToWatch.size(); rowNr++) - mdl->setValue(var, varsToWatch[rowNr].max, rowNr); + mdl->setValue(variable.var, varsToWatch[rowNr].max, rowNr); return true; default: return false; }}); - ui->initNumber(tableVar, "value", UINT16_MAX, 0, 255, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "value", UINT16_MAX, 0, 255, true, [this](EventArguments) { switch (eventType) { case onSetValue: for (size_t rowNr = 0; rowNr < varsToWatch.size(); rowNr++) - mdl->setValue(var, varsToWatch[rowNr].savedValue, rowNr); + mdl->setValue(variable.var, varsToWatch[rowNr].savedValue, rowNr); return true; default: return false; }}); diff --git a/src/User/UserModLive.cpp b/src/User/UserModLive.cpp index a96f4a5..faddaf9 100644 --- a/src/User/UserModLive.cpp +++ b/src/User/UserModLive.cpp @@ -12,7 +12,6 @@ #ifdef STARBASE_USERMOD_LIVE //don't know why to exclude the .cpp as the .h is not included in this case ... #include "UserModLive.h" -#include "ESPLiveScript.h" //note: contains declarations AND definitions, therefore can only be included once! // #include @@ -23,6 +22,8 @@ // #define __RUN_CORE 0 +#include "ESPLiveScript.h" //note: contains declarations AND definitions, therefore can only be included once! + long time1; long time4; static float _min = 9999; @@ -116,17 +117,17 @@ static float _time(float j) { parentVar = ui->initUserMod(parentVar, name, 6310); - ui->initSelect(parentVar, "script", UINT8_MAX, false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initSelect(parentVar, "script", UINT8_MAX, false, [this](EventArguments) { switch (eventType) { case onUI: { - // ui->setComment(var, "Fixture to display effect on"); - JsonArray options = ui->setOptions(var); + // variable.setComment("Fixture to display effect on"); + JsonArray options = variable.setOptions(); options.add("None"); files->dirToJson(options, true, ".sc"); //only files containing F(ixture), alphabetically return true; } case onChange: { //set script - uint8_t fileNr = var["value"]; + uint8_t fileNr = variable.value(); ppf("%s script.onChange f:%d\n", name, fileNr); @@ -164,15 +165,15 @@ static float _time(float j) { default: return false; }}); //script - ui->initText(parentVar, "fps1", nullptr, 10, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "fps1", nullptr, 10, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%.0f /s", fps, 0); //0 is to force format overload used + mdl->setValue(variable.var, "%.0f /s", fps, 0); //0 is to force format overload used return true; default: return false; }}); - ui->initText(parentVar, "fps2", nullptr, 10, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(parentVar, "fps2", nullptr, 10, true, [this](EventArguments) { switch (eventType) { case onLoop1s: - mdl->setValue(var, "%d /s", frameCounter, 0); //0 is to force format overload used + mdl->setValue(variable.var, "%d /s", frameCounter, 0); //0 is to force format overload used frameCounter = 0; return true; default: return false; @@ -180,77 +181,77 @@ static float _time(float j) { JsonObject tableVar = ui->initTable(parentVar, "scripts", nullptr, true); - ui->initText(tableVar, "name", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "name", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { const char *name = exec.name.c_str(); - mdl->setValue(var, JsonString(exec.name.c_str(), JsonString::Copied), rowNr++); + mdl->setValue(variable.var, JsonString(exec.name.c_str(), JsonString::Copied), rowNr++); } return true; default: return false; }}); - ui->initCheckBox(tableVar, "running", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(tableVar, "running", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { - mdl->setValue(var, exec.isRunning(), rowNr++); + mdl->setValue(variable.var, exec.isRunning(), rowNr++); } return true; default: return false; }}); - ui->initCheckBox(tableVar, "halted", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(tableVar, "halted", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { - mdl->setValue(var, exec.isHalted, rowNr++); + mdl->setValue(variable.var, exec.isHalted, rowNr++); } return true; default: return false; }}); - ui->initCheckBox(tableVar, "exe", UINT8_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(tableVar, "exe", UINT8_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { - mdl->setValue(var, exec.exeExist, rowNr++); + mdl->setValue(variable.var, exec.exeExist, rowNr++); } return true; default: return false; }}); - ui->initNumber(tableVar, "handle", UINT16_MAX, 0, UINT16_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initNumber(tableVar, "handle", UINT16_MAX, 0, UINT16_MAX, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { - mdl->setValue(var, exec.__run_handle_index, rowNr++); + mdl->setValue(variable.var, exec.__run_handle_index, rowNr++); } return true; default: return false; }}); - ui->initText(tableVar, "size", nullptr, 32, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initText(tableVar, "size", nullptr, 32, true, [this](EventArguments) { switch (eventType) { case onSetValue: - var["value"].to(); web->addResponse(var, "value", var["value"]); // empty the value + variable.var["value"].to(); web->addResponse(variable.var, "value", variable.value()); // empty the value rowNr = 0; for (Executable &exec: scriptRuntime._scExecutables) { exe_info exeInfo = scriptRuntime.getExecutableInfo(exec.name); char text[30]; print->fFormat(text, sizeof(text), "%d+%d=%d B", exeInfo.binary_size, exeInfo.data_size, exeInfo.total_size); - mdl->setValue(var, JsonString(text, JsonString::Copied), rowNr++); + mdl->setValue(variable.var, JsonString(text, JsonString::Copied), rowNr++); } return true; default: return false; }}); - ui->initButton(tableVar, "Kill", false, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initButton(tableVar, "Kill", false, [this](EventArguments) { switch (eventType) { case onChange: if (rowNr < scriptRuntime._scExecutables.size()) killAndDelete(scriptRuntime._scExecutables[rowNr].name.c_str()); diff --git a/src/User/UserModMPU6050.h b/src/User/UserModMPU6050.h index 24c5c49..0e5025f 100644 --- a/src/User/UserModMPU6050.h +++ b/src/User/UserModMPU6050.h @@ -36,29 +36,29 @@ class UserModMPU6050: public SysModule { SysModule::setup(); parentVar = ui->initUserMod(parentVar, name, 6305); - ui->initCheckBox(parentVar, "ready", &motionTrackingReady, true, [](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCheckBox(parentVar, "ready", &motionTrackingReady, true, [](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "tracking ready"); + variable.setComment("tracking ready"); return true; default: return false; }}); - ui->initCoord3D(parentVar, "gyro", &gyro, 0, UINT16_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCoord3D(parentVar, "gyro", &gyro, 0, UINT16_MAX, true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "in degrees"); + variable.setComment("in degrees"); return true; case onLoop1s: - mdl->setValue(var, gyro); //automatic as var is referenced??? + mdl->setValue(variable.var, gyro); //automatic as var is referenced??? return true; default: return false; }}); - ui->initCoord3D(parentVar, "accell", &accell, 0, UINT16_MAX, true, [this](JsonObject var, uint8_t rowNr, uint8_t funType) { switch (funType) { //varFun + ui->initCoord3D(parentVar, "accell", &accell, 0, UINT16_MAX, true, [this](EventArguments) { switch (eventType) { case onUI: - ui->setComment(var, "in m/sĀ²"); + variable.setComment("in m/sĀ²"); return true; case onLoop1s: - mdl->setValue(var, accell); //automatic as var is referenced??? + mdl->setValue(variable.var, accell); //automatic as var is referenced??? return true; default: return false; }});