Skip to content

Commit

Permalink
Support for variables with values by reference
Browse files Browse the repository at this point in the history
SysModFiles, SysModInstances, SysModPins, SysModSystem, SysModUI, SysModWeb, UserMod131
- callVarFun parameters

SysModModel
- doWriteModel: exclude pointers in saved model
- rename setValueChangeFun to callVarChangeFun
- callVarChangeFun add init parameter, add pointer handling

SysModUI
- add initNumber, initSlider, initCheckBox, initSelect for referenced values
- initVarAndUpdate: support pointer, assign to ["p"]
- initVarAndUpdate: use callVarChangeFun (support for ["p"]
  • Loading branch information
ewoudwijma committed Jun 4, 2024
1 parent 593cb2a commit fc1bf85
Show file tree
Hide file tree
Showing 12 changed files with 107 additions and 122 deletions.
2 changes: 1 addition & 1 deletion data/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -631,7 +631,7 @@ function receiveData(json) {
let variable = value.var;
let rowNr = value.rowNr == null?UINT8_MAX:value.rowNr;
let nodeId = variable.id + ((rowNr != UINT8_MAX)?"#" + rowNr:"");
//if var object with .n, create .n (e.g. see setEffect and fixtureGenChFun, tbd: )
//if var object with .n, create .n (e.g. see fx.changefun (setEffect) and fixtureGenChFun, tbd: )
ppf("receiveData details", key, variable.id, nodeId, rowNr);
if (gId(nodeId + "_n")) gId(nodeId + "_n").remove(); //remove old ndiv

Expand Down
2 changes: 1 addition & 1 deletion platformio.ini
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ lib_deps =
build_flags =
-D APP=StarBase
-D PIOENV=$PIOENV
-D VERSION=24060110 ; Date and time (GMT!), update at every commit!!
-D VERSION=24060410 ; Date and time (GMT!), update at every commit!!
-D CONFIG_ASYNC_TCP_USE_WDT=0
-D LFS_THREADSAFE ; enables use of semaphores in LittleFS driver
-D STARBASE_DEVMODE
Expand Down
6 changes: 3 additions & 3 deletions src/Sys/SysModFiles.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -131,15 +131,15 @@ void SysModFiles::loop() {
}
root.close();

ui->callVarFun(mdl->findVar("drsize")); //valueFun
ui->callVarFun("drsize");

for (JsonObject childVar: mdl->varChildren("fileTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun);
ui->callVarFun(childVar);
}
}

void SysModFiles::loop10s() {
ui->callVarFun(mdl->findVar("drsize"));
ui->callVarFun("drsize");
}

bool SysModFiles::remove(const char * path) {
Expand Down
16 changes: 8 additions & 8 deletions src/Sys/SysModInstances.h
Original file line number Diff line number Diff line change
Expand Up @@ -464,7 +464,7 @@ class SysModInstances:public SysModule {

ppf("insTbl handleNotifications %d\n", notifierUdp.remoteIP()[3]);
for (JsonObject childVar: mdl->varChildren("insTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun); //rowNr //instance - instances.begin()
ui->callVarFun(childVar); //rowNr //instance - instances.begin()

web->recvUDPCounter++;
web->recvUDPBytes+=packetSize;
Expand Down Expand Up @@ -558,10 +558,10 @@ class SysModInstances:public SysModule {
if (erased) {
ppf("insTbl remove inactive instances\n");
for (JsonObject childVar: mdl->varChildren("insTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun); //no rowNr so all rows updated
ui->callVarFun(childVar); //no rowNr so all rows updated

ui->callVarFun("ddpInst", UINT8_MAX, f_UIFun);
ui->callVarFun("artInst", UINT8_MAX, f_UIFun);
ui->callVarFun("ddpInst", UINT8_MAX, f_UIFun); //rebuild options
ui->callVarFun("artInst", UINT8_MAX, f_UIFun); //rebuild options
}
}

Expand Down Expand Up @@ -796,7 +796,7 @@ class SysModInstances:public SysModule {
// ppf("updateInstance updRow\n");

for (JsonObject childVar: mdl->varChildren("insTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun); //rowNr instance - instances.begin()
ui->callVarFun(childVar); //rowNr instance - instances.begin()

//tbd: now done for all rows, should be done only for updated rows!
}
Expand All @@ -808,15 +808,15 @@ class SysModInstances:public SysModule {
if (!instanceFound) {
ppf("insTbl new instance %s\n", messageIP.toString().c_str());

ui->callVarFun("ddpInst", UINT8_MAX, f_UIFun); //UiFun as select changes
ui->callVarFun("artInst", UINT8_MAX, f_UIFun);
ui->callVarFun("ddpInst", UINT8_MAX, f_UIFun); //rebuild options
ui->callVarFun("artInst", UINT8_MAX, f_UIFun); //rebuild options

// ui->processUiFun("insTbl");
//run though it sorted to find the right rowNr
// for (std::vector<InstanceInfo>::iterator instance=instances.begin(); instance!=instances.end(); ++instance) {
// if (instance->ip == messageIP) {
for (JsonObject childVar: mdl->varChildren("insTbl")) {
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun); //no rowNr, update all
ui->callVarFun(childVar); //no rowNr, update all
}
// }
// }
Expand Down
55 changes: 45 additions & 10 deletions src/Sys/SysModModel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -48,13 +48,10 @@ void SysModModel::setup() {

#ifdef STARBASE_DEVMODE

ui->initCheckBox(parentVar, "showObsolete", doShowObsolete, false, [this](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
ui->initCheckBox(parentVar, "showObsolete", &doShowObsolete, false, [this](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
case f_UIFun:
ui->setComment(var, "Show in UI (refresh)");
return true;
case f_ChangeFun:
doShowObsolete = var["value"];
return true;
default: return false;
}});

Expand Down Expand Up @@ -92,7 +89,8 @@ void SysModModel::setup() {
StarJson starJson("/model.json", "w"); //open fileName for deserialize
starJson.addExclusion("fun");
starJson.addExclusion("dash");
starJson.addExclusion("o");
starJson.addExclusion("o"); //order
starJson.addExclusion("p"); //pointers
starJson.writeJsonDocToFile(model);

// print->printJson("Write model", *model); //this shows the model before exclusion
Expand Down Expand Up @@ -238,12 +236,49 @@ bool checkDash(JsonObject var) {
return false;
}

void SysModModel::setValueChangeFun(JsonObject var, unsigned8 rowNr) {
//done here as ui cannot be used in SysModModel.h
if (checkDash(var))
instances->changedVarsQueue.push_back(var);
bool SysModModel::callVarChangeFun(JsonObject var, unsigned8 rowNr, bool init) {
//not in SysModModel.h as ui->callVarFun cannot be used in SysModModel.h

if (!init) {
if (checkDash(var))
instances->changedVarsQueue.push_back(var); //tbd: check value arrays / rowNr is working
}

//if var is bound by pointer, set the pointer value before calling changeFun
if (!var["p"].isNull()) {
JsonVariant value;
int pointer;
if (rowNr == UINT8_MAX) {
value = var["value"];
pointer = var["p"];
} else {
value = var["value"][rowNr];
pointer = var["p"][rowNr];
}

if (var["type"] == "select" || var["type"] == "checkbox" || var["type"] == "range") {
uint8_t *valuePointer = (uint8_t *)pointer;
if (valuePointer != nullptr) {
*valuePointer = value;
ppf("pointer set8 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", varID(var), *valuePointer, valuePointer, rowNr, var["value"].as<String>().c_str(), pointer);
}
else
ppf("dev pointer set8 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", varID(var), *valuePointer, valuePointer, rowNr, var["value"].as<String>().c_str(), pointer);
}
else if (var["type"] == "number") {
uint16_t *valuePointer = (uint16_t *)pointer;
if (valuePointer != nullptr) {
*valuePointer = value;
ppf("pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", varID(var), *valuePointer, valuePointer, rowNr, var["value"].as<String>().c_str(), pointer);
}
else
ppf("dev pointer set16 %s: v:%d (p:%p) (r:%d v:%s p:%d)\n", varID(var), *valuePointer, valuePointer, rowNr, var["value"].as<String>().c_str(), pointer);
}
else
ppf("dev pointer of type %s not supported yet\n", var["type"].as<String>().c_str());
}

ui->callVarFun(var, rowNr, f_ChangeFun);
return ui->callVarFun(var, rowNr, f_ChangeFun);

// web->sendResponseObject();
}
8 changes: 4 additions & 4 deletions src/Sys/SysModModel.h
Original file line number Diff line number Diff line change
Expand Up @@ -239,7 +239,7 @@ class SysModModel:public SysModule {
//trick to remove null values
if (var["value"].isNull() || var["value"].as<unsigned16>() == UINT16_MAX) {
var.remove("value");
ppf("dev setValue value removed %s %s\n", varID(var), var["oldValue"].as<String>().c_str());
// ppf("dev setValue value removed %s %s\n", varID(var), var["oldValue"].as<String>().c_str());
}
else {
//only print if ! read only
Expand Down Expand Up @@ -282,7 +282,7 @@ class SysModModel:public SysModule {
}
}

if (changed) setValueChangeFun(var, rowNr);
if (changed) callVarChangeFun(var, rowNr);

return var;
}
Expand Down Expand Up @@ -349,8 +349,8 @@ class SysModModel:public SysModule {
//recursively add values in a variant
void varToValues(JsonObject var, JsonArray values);

//run the change function and send response to all? websocket clients
void setValueChangeFun(JsonObject var, unsigned8 rowNr = UINT8_MAX);
//sends dash var change to udp (if init), sets pointer if pointer var and run changeFun
bool callVarChangeFun(JsonObject var, unsigned8 rowNr = UINT8_MAX, bool init = false);

//pseudo VarObject: public JsonObject functions
const char * varID(JsonObject var) {return var["id"];}
Expand Down
2 changes: 1 addition & 1 deletion src/Sys/SysModPins.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,7 @@ void SysModPins::loop() {
pinsChanged = false;

for (JsonObject childVar: mdl->varChildren("pinTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun);
ui->callVarFun(childVar);
}
}

Expand Down
8 changes: 4 additions & 4 deletions src/Sys/SysModSystem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -237,12 +237,12 @@ void SysModSystem::loop1s() {
loopCounter = 0;
}
void SysModSystem::loop10s() {
ui->callVarFun(mdl->findVar("heap"));
ui->callVarFun(mdl->findVar("mainStack"));
ui->callVarFun(mdl->findVar("tcpStack"));
ui->callVarFun("heap");
ui->callVarFun("mainStack");
ui->callVarFun("tcpStack");

if (psramFound()) {
ui->callVarFun(mdl->findVar("psram"));
ui->callVarFun("psram");
}

//heartbeat
Expand Down
4 changes: 2 additions & 2 deletions src/Sys/SysModUI.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ void SysModUI::loop() {

void SysModUI::loop1s() {
//if something changed in vloops
callVarFun("vlLoopps", UINT8_MAX, f_ValueFun);
callVarFun("vlLoopps");
for (VarLoop &varLoop : loopFunctions)
varLoop.counter = 0;
}
Expand Down Expand Up @@ -232,7 +232,7 @@ void SysModUI::processJson(JsonVariant json) {
{
//a button never sets the value
if (var["type"] == "button") { //button always
callVarFun(var, rowNr, f_ChangeFun);
mdl->callVarChangeFun(var, rowNr);
if (rowNr != UINT8_MAX) web->getResponseObject()[mdl->varID(var)]["rowNr"] = rowNr;
}
else {
Expand Down
46 changes: 32 additions & 14 deletions src/Sys/SysModUI.h
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,10 @@ class SysModUI: public SysModule {
JsonObject initNumber(JsonObject parent, const char * id, int value = UINT16_MAX, int min = 0, int max = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "number", value, min, max, readOnly, varFun);
}
//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 initVarAndUpdate<uint16_t>(parent, id, "number", value, min, max, readOnly, varFun);
}

JsonObject initPin(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "pin", value, 0, NUM_DIGITAL_PINS, readOnly, varFun);
Expand All @@ -100,6 +104,10 @@ class SysModUI: public SysModule {
JsonObject initSlider(JsonObject parent, const char * id, int value = UINT16_MAX, int min = 0, int max = 255, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "range", value, min, max, readOnly, varFun);
}
//init a range slider using referenced value
JsonObject initSlider(JsonObject parent, const char * id, unsigned8 * value = nullptr, int min = 0, int max = 255, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<unsigned8>(parent, id, "range", value, min, max, readOnly, varFun);
}

JsonObject initCanvas(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "canvas", value, 0, 0, readOnly, varFun);
Expand All @@ -109,6 +117,10 @@ class SysModUI: public SysModule {
JsonObject initCheckBox(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "checkbox", value, 0, 0, readOnly, varFun);
}
//init a checkbox using referenced value
JsonObject initCheckBox(JsonObject parent, const char * id, bool * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<bool>(parent, id, "checkbox", value, 0, 0, readOnly, varFun);
}

//a button never gets a value
JsonObject initButton(JsonObject parent, const char * id, bool readOnly = false, VarFun varFun = nullptr) {
Expand All @@ -119,16 +131,15 @@ class SysModUI: public SysModule {
JsonObject initSelect(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "select", value, 0, 0, readOnly, varFun);
}
//init a select using referenced value
JsonObject initSelect(JsonObject parent, const char * id, unsigned8 * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<unsigned8>(parent, id, "select", value, 0, 0, readOnly, varFun);
}

JsonObject initIP(JsonObject parent, const char * id, int value = UINT16_MAX, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<int>(parent, id, "ip", value, 0, 255, readOnly, varFun);
}

//WIP pointer values
JsonObject initSelect(JsonObject parent, const char * id, unsigned8 * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<unsigned8>(parent, id, "select", value, 0, 0, readOnly, varFun);
}

JsonObject initTextArea(JsonObject parent, const char * id, const char * value = nullptr, bool readOnly = false, VarFun varFun = nullptr) {
return initVarAndUpdate<const char *>(parent, id, "textarea", value, 0, 0, readOnly, varFun);
}
Expand All @@ -137,18 +148,23 @@ class SysModUI: public SysModule {
return initVarAndUpdate<const char *>(parent, id, "url", value, 0, 0, readOnly, varFun);
}

//WIP pointer values
//initVarAndUpdate using referenced value
template <typename Type>
JsonObject initVarAndUpdate(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 var = initVarAndUpdate(parent, id, type, *value, min, max, readOnly, varFun);
// var["p"] = (const char *)value; //store pointer!
JsonObject var = initVarAndUpdate(parent, id, type, *value, min, max, readOnly, varFun, (int)value); //call with extra parameter: int of the pointer
return var;
}

template <typename Type>
JsonObject initVarAndUpdate(JsonObject parent, const char * id, const char * type, Type value, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr) {
JsonObject initVarAndUpdate(JsonObject parent, const char * id, const char * type, Type value, int min = 0, int max = 255, bool readOnly = true, VarFun varFun = nullptr, int pointer = 0) {
JsonObject var = initVar(parent, id, type, readOnly, varFun);
if (pointer != 0) {
if (mdl->setValueRowNr == UINT8_MAX)
var["p"] = pointer; //store pointer!
else
var["p"][mdl->setValueRowNr] = pointer; //store pointer in array!
ppf("pointer stored %s: %s\n", id, (void *)(var["p"].as<String>().c_str()));
}
if (min) var["min"] = min;
if (max && max != UINT16_MAX) var["max"] = max;

Expand Down Expand Up @@ -184,11 +200,11 @@ class SysModUI: public SysModule {
if (var["value"].is<JsonArray>()) {
int rowNr = 0;
for (JsonVariant val:var["value"].as<JsonArray>()) {
changeFunExists |= varFun(var, rowNr++, f_ChangeFun);
changeFunExists |= mdl->callVarChangeFun(var, rowNr++, true); //init, also set var["p"]
}
}
else {
changeFunExists = varFun(var, UINT8_MAX, f_ChangeFun); //if no rowNr use rowNr 0
changeFunExists = mdl->callVarChangeFun(var, UINT8_MAX, true); //init, also set var["p"]
}

if (changeFunExists)
Expand All @@ -201,11 +217,13 @@ class SysModUI: public SysModule {

JsonObject initVar(JsonObject parent, const char * id, const char * type, bool readOnly = true, VarFun varFun = nullptr);

bool callVarFun(const char * varID, unsigned8 rowNr = UINT8_MAX, unsigned8 funType = f_ChangeFun) {
//checks if var has fun of type funType implemented by calling it and checking result (for uiFun on RO var, also valueFun is called)
bool callVarFun(const char * varID, unsigned8 rowNr = UINT8_MAX, unsigned8 funType = f_ValueFun) {
JsonObject var = mdl->findVar(varID);
return callVarFun(var, rowNr, funType);
}

//checks if var has fun of type funType implemented by calling it and checking result (for uiFun on RO var, also valueFun is called)
bool callVarFun(JsonObject var, unsigned8 rowNr = UINT8_MAX, unsigned8 funType = f_ValueFun) {
bool result = false;

Expand Down Expand Up @@ -274,7 +292,7 @@ class SysModUI: public SysModule {
}
//return the options from valueFun (don't forget to clear responseObject)
JsonArray getOptions(JsonObject var) {
callVarFun(var, UINT8_MAX, f_UIFun); //tricky: fills the options table
callVarFun(var, UINT8_MAX, f_UIFun); //rebuild options
return web->getResponseObject()[mdl->varID(var)]["options"];
}
void clearOptions(JsonObject var) {
Expand Down
4 changes: 2 additions & 2 deletions src/Sys/SysModWeb.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -160,14 +160,14 @@ void SysModWeb::loop() {

// ppf("SysModWeb clientsChanged\n");
for (JsonObject childVar: mdl->varChildren("clTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun);
ui->callVarFun(childVar);
}

}

void SysModWeb::loop1s() {
for (JsonObject childVar: mdl->varChildren("clTbl"))
ui->callVarFun(childVar, UINT8_MAX, f_ValueFun);
ui->callVarFun(childVar);

mdl->setUIValueV("wsSend", "#: %d /s T: %d B/s B:%d B/s", sendWsCounter, sendWsTBytes, sendWsBBytes);
sendWsCounter = 0;
Expand Down
Loading

0 comments on commit fc1bf85

Please sign in to comment.