mirror of
https://github.com/lumapu/ahoy.git
synced 2025-05-31 09:46:12 +02:00
improved stability
added icons to index.html, added wifi-strength symbol on each page moved packet stats and sun to system.html refactored communication offset (adjustable in minutes now)
This commit is contained in:
parent
07c75b544c
commit
5977bbaee6
20 changed files with 317 additions and 135 deletions
|
@ -1,5 +1,11 @@
|
|||
# Changelog
|
||||
|
||||
## 0.5.57
|
||||
* improved stability
|
||||
* added icons to index.html, added wifi-strength symbol on each page
|
||||
* moved packet stats and sun to system.html
|
||||
* refactored communication offset (adjustable in minutes now)
|
||||
|
||||
## 0.5.56
|
||||
* factory reset formats entire little fs
|
||||
* renamed sunrise / sunset on indext.html to start / stop communication
|
||||
|
|
12
src/app.cpp
12
src/app.cpp
|
@ -37,7 +37,7 @@ void app::setup() {
|
|||
|
||||
|
||||
#if !defined(AP_ONLY)
|
||||
mMqtt.setup(&mConfig->mqtt, mConfig->sys.deviceName, mVersion, mSys, &mTimestamp, &mSunrise, &mSunset);
|
||||
mMqtt.setup(&mConfig->mqtt, mConfig->sys.deviceName, mVersion, mSys, &mTimestamp);
|
||||
#endif
|
||||
|
||||
mWifi.setup(mConfig, &mTimestamp);
|
||||
|
@ -126,7 +126,9 @@ void app::loop(void) {
|
|||
mPayload.process(true, mConfig->nrf.maxRetransPerPyld, &mStat);
|
||||
}
|
||||
|
||||
#if !defined(AP_ONLY)
|
||||
mMqtt.loop();
|
||||
#endif
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -149,9 +151,9 @@ void app::tickCalcSunrise(void) {
|
|||
uint32_t nxtTrig = mTimestamp - ((mTimestamp - 10) % 86400) + 86400; // next midnight, -10 for safety that it is certain next day
|
||||
onceAt(std::bind(&app::tickCalcSunrise, this), nxtTrig);
|
||||
if (mConfig->mqtt.broker[0] > 0) {
|
||||
once(std::bind(&PubMqttType::tickerSun, &mMqtt), 1);
|
||||
onceAt(std::bind(&PubMqttType::tickSunrise, &mMqtt), mSunrise);
|
||||
onceAt(std::bind(&PubMqttType::tickSunset, &mMqtt), mSunset);
|
||||
mMqtt.tickerSun(mSunrise, mSunset, mConfig->sun.offsetSec);
|
||||
onceAt(std::bind(&PubMqttType::tickSunrise, &mMqtt), (mSunrise - mConfig->sun.offsetSec));
|
||||
onceAt(std::bind(&PubMqttType::tickSunset, &mMqtt), (mSunset + mConfig->sun.offsetSec));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -161,7 +163,7 @@ void app::tickSend(void) {
|
|||
DPRINTLN(DBG_WARN, "NRF24 not connected!");
|
||||
return;
|
||||
}
|
||||
if ((mTimestamp > 0) && (!mConfig->sun.disNightCom || (mTimestamp >= mSunrise && mTimestamp <= mSunset))) { // Timestamp is set and (inverter communication only during the day if the option is activated and sunrise/sunset is set)
|
||||
if ((mTimestamp > 0) && (!mConfig->sun.disNightCom || (mTimestamp >= (mSunrise - mConfig->sun.offsetSec) && mTimestamp <= (mSunset + mConfig->sun.offsetSec)))) { // Timestamp is set and (inverter communication only during the day if the option is activated and sunrise/sunset is set)
|
||||
if (!mSys->BufCtrl.empty()) {
|
||||
if (mConfig->serial.debug)
|
||||
DPRINTLN(DBG_DEBUG, F("recbuf not empty! #") + String(mSys->BufCtrl.getFill()));
|
||||
|
|
|
@ -74,6 +74,7 @@ class app : public IApp, public ah::Scheduler {
|
|||
}
|
||||
|
||||
bool saveSettings() {
|
||||
mShowRebootRequest = true;
|
||||
return mSettings.saveSettings();
|
||||
}
|
||||
|
||||
|
|
|
@ -55,6 +55,7 @@ typedef struct {
|
|||
float lat;
|
||||
float lon;
|
||||
bool disNightCom; // disable night communication
|
||||
uint16_t offsetSec;
|
||||
} cfgSun_t;
|
||||
|
||||
typedef struct {
|
||||
|
@ -173,7 +174,7 @@ class settings {
|
|||
//fp.seek(0, SeekSet);
|
||||
DynamicJsonDocument root(4096);
|
||||
DeserializationError err = deserializeJson(root, fp);
|
||||
if(!err) {
|
||||
if(!err && (root.size() > 0)) {
|
||||
mCfg.valid = true;
|
||||
jsonWifi(root["wifi"]);
|
||||
jsonNrf(root["nrf"]);
|
||||
|
@ -262,6 +263,7 @@ class settings {
|
|||
mCfg.sun.lat = 0.0;
|
||||
mCfg.sun.lon = 0.0;
|
||||
mCfg.sun.disNightCom = false;
|
||||
mCfg.sun.offsetSec = 0;
|
||||
|
||||
mCfg.serial.interval = SERIAL_INTERVAL;
|
||||
mCfg.serial.showIv = false;
|
||||
|
@ -334,13 +336,15 @@ class settings {
|
|||
|
||||
void jsonSun(JsonObject obj, bool set = false) {
|
||||
if(set) {
|
||||
obj[F("lat")] = mCfg.sun.lat;
|
||||
obj[F("lon")] = mCfg.sun.lon;
|
||||
obj[F("dis")] = mCfg.sun.disNightCom;
|
||||
obj[F("lat")] = mCfg.sun.lat;
|
||||
obj[F("lon")] = mCfg.sun.lon;
|
||||
obj[F("dis")] = mCfg.sun.disNightCom;
|
||||
obj[F("offs")] = mCfg.sun.offsetSec;
|
||||
} else {
|
||||
mCfg.sun.lat = obj[F("lat")];
|
||||
mCfg.sun.lon = obj[F("lon")];
|
||||
mCfg.sun.disNightCom = obj[F("dis")];
|
||||
mCfg.sun.offsetSec = obj[F("offs")];
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
//-------------------------------------
|
||||
#define VERSION_MAJOR 0
|
||||
#define VERSION_MINOR 5
|
||||
#define VERSION_PATCH 56
|
||||
#define VERSION_PATCH 57
|
||||
|
||||
//-------------------------------------
|
||||
typedef struct {
|
||||
|
|
|
@ -297,6 +297,8 @@ class HmRadio {
|
|||
}
|
||||
|
||||
uint8_t getDataRate(void) {
|
||||
if(!mNrf24.isChipConnected())
|
||||
return 3; // unkown
|
||||
return mNrf24.getDataRate();
|
||||
}
|
||||
|
||||
|
|
|
@ -104,8 +104,14 @@ class HmSystem {
|
|||
}
|
||||
|
||||
uint8_t getNumInverters(void) {
|
||||
DPRINTLN(DBG_VERBOSE, F("hmSystem.h:getNumInverters"));
|
||||
return mNumInv;
|
||||
uint8_t num = 0;
|
||||
INVERTERTYPE *p;
|
||||
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i++) {
|
||||
p = &mInverter[i];
|
||||
if(p->config->serial.u64 != 0ULL)
|
||||
num++;
|
||||
}
|
||||
return num;
|
||||
}
|
||||
|
||||
void enableDebug() {
|
||||
|
|
|
@ -40,14 +40,12 @@ class PubMqtt {
|
|||
|
||||
~PubMqtt() { }
|
||||
|
||||
void setup(cfgMqtt_t *cfg_mqtt, const char *devName, const char *version, HMSYSTEM *sys, uint32_t *utcTs, uint32_t *sunrise, uint32_t *sunset) {
|
||||
void setup(cfgMqtt_t *cfg_mqtt, const char *devName, const char *version, HMSYSTEM *sys, uint32_t *utcTs) {
|
||||
mCfgMqtt = cfg_mqtt;
|
||||
mDevName = devName;
|
||||
mVersion = version;
|
||||
mSys = sys;
|
||||
mUtcTimestamp = utcTs;
|
||||
mSunrise = sunrise;
|
||||
mSunset = sunset;
|
||||
|
||||
snprintf(mLwtTopic, MQTT_TOPIC_LEN + 5, "%s/mqtt", mCfgMqtt->topic);
|
||||
|
||||
|
@ -93,9 +91,11 @@ class PubMqtt {
|
|||
tickSunset();
|
||||
}
|
||||
|
||||
void tickerSun() {
|
||||
publish("sunrise", String(*mSunrise).c_str(), true);
|
||||
publish("sunset", String(*mSunset).c_str(), true);
|
||||
void tickerSun(uint32_t sunrise, uint32_t sunset, uint32_t offs) {
|
||||
publish("sunrise", String(sunrise).c_str(), true);
|
||||
publish("sunset", String(sunset).c_str(), true);
|
||||
publish("comm_start", String(sunrise - offs).c_str(), true);
|
||||
publish("comm_stop", String(sunset + offs).c_str(), true);
|
||||
}
|
||||
|
||||
void tickSunrise() {
|
||||
|
@ -505,7 +505,6 @@ class PubMqtt {
|
|||
WiFiEventHandler mHWifiCon, mHWifiDiscon;
|
||||
#endif
|
||||
|
||||
uint32_t *mSunrise, *mSunset;
|
||||
HMSYSTEM *mSys;
|
||||
uint32_t *mUtcTimestamp;
|
||||
uint32_t mRxCnt, mTxCnt;
|
||||
|
|
|
@ -25,7 +25,7 @@ namespace ah {
|
|||
// Declination of the sun
|
||||
double delta = ASIN(SIN(lambda) * SIN(23.44));
|
||||
// Hour angle
|
||||
double omega = ACOS((SIN(-3.5) - SIN(lat) * SIN(delta)) / (COS(lat) * COS(delta))); //(SIN(-0.83)
|
||||
double omega = ACOS((SIN(-0.83) - SIN(lat) * SIN(delta)) / (COS(lat) * COS(delta)));
|
||||
// Calculate sunrise and sunset
|
||||
double Jrise = Jtransit - omega / 360;
|
||||
double Jset = Jtransit + omega / 360;
|
||||
|
|
|
@ -60,6 +60,7 @@ class RestApi {
|
|||
else if(path == "html/logout") getHtmlLogout(root);
|
||||
else if(path == "html/save") getHtmlSave(root);
|
||||
else if(path == "system") getSysInfo(root);
|
||||
else if(path == "generic") getGeneric(root);
|
||||
else if(path == "reboot") getReboot(root);
|
||||
else if(path == "statistics") getStatistics(root);
|
||||
else if(path == "inverter/list") getInverterList(root);
|
||||
|
@ -144,17 +145,23 @@ class RestApi {
|
|||
request->send(response);
|
||||
}
|
||||
|
||||
void getGeneric(JsonObject obj) {
|
||||
obj[F("version")] = String(mApp->getVersion());
|
||||
obj[F("build")] = String(AUTO_GIT_HASH);
|
||||
obj[F("wifi_rssi")] = (WiFi.status() != WL_CONNECTED) ? 0 : WiFi.RSSI();
|
||||
obj[F("ts_uptime")] = mApp->getUptime();
|
||||
|
||||
#if defined(ESP32)
|
||||
obj[F("esp_type")] = F("ESP32");
|
||||
#else
|
||||
obj[F("esp_type")] = F("ESP8266");
|
||||
#endif
|
||||
}
|
||||
|
||||
void getSysInfo(JsonObject obj) {
|
||||
obj[F("ssid")] = mConfig->sys.stationSsid;
|
||||
obj[F("device_name")] = mConfig->sys.deviceName;
|
||||
obj[F("version")] = String(mApp->getVersion());
|
||||
obj[F("build")] = String(AUTO_GIT_HASH);
|
||||
|
||||
obj[F("ts_uptime")] = mApp->getUptime();
|
||||
obj[F("ts_now")] = mApp->getTimestamp();
|
||||
obj[F("ts_sunrise")] = mApp->getSunrise();
|
||||
obj[F("ts_sunset")] = mApp->getSunset();
|
||||
obj[F("wifi_rssi")] = WiFi.RSSI();
|
||||
obj[F("mac")] = WiFi.macAddress();
|
||||
obj[F("hostname")] = WiFi.getHostname();
|
||||
obj[F("pwd_set")] = (strlen(mConfig->sys.adminPwd) > 0);
|
||||
|
@ -164,9 +171,10 @@ class RestApi {
|
|||
obj[F("heap_free")] = ESP.getFreeHeap();
|
||||
obj[F("sketch_total")] = ESP.getFreeSketchSpace();
|
||||
obj[F("sketch_used")] = ESP.getSketchSize() / 1024; // in kb
|
||||
|
||||
getGeneric(obj);
|
||||
|
||||
getRadio(obj.createNestedObject(F("radio")));
|
||||
getStatistics(obj.createNestedObject(F("statistics")));
|
||||
|
||||
#if defined(ESP32)
|
||||
obj[F("heap_total")] = ESP.getHeapSize();
|
||||
|
@ -191,24 +199,19 @@ class RestApi {
|
|||
#endif
|
||||
//obj[F("littlefs_total")] = LittleFS.totalBytes();
|
||||
//obj[F("littlefs_used")] = LittleFS.usedBytes();
|
||||
|
||||
#if defined(ESP32)
|
||||
obj[F("esp_type")] = F("ESP32");
|
||||
#else
|
||||
obj[F("esp_type")] = F("ESP8266");
|
||||
#endif
|
||||
}
|
||||
|
||||
void getHtmlSystem(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
obj[F("html")] = F("<a href=\"/factory\" class=\"btn\">Factory Reset</a><br/><br/><a href=\"/reboot\" class=\"btn\">Reboot</a>");
|
||||
|
||||
}
|
||||
|
||||
void getHtmlLogout(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
obj[F("refresh")] = 3;
|
||||
obj[F("refresh_url")] = "/";
|
||||
obj[F("html")] = F("succesfully logged out");
|
||||
|
@ -216,7 +219,7 @@ class RestApi {
|
|||
|
||||
void getHtmlSave(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
obj[F("refresh")] = 2;
|
||||
obj[F("refresh_url")] = "/setup";
|
||||
obj[F("html")] = F("settings succesfully save");
|
||||
|
@ -224,7 +227,7 @@ class RestApi {
|
|||
|
||||
void getReboot(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
obj[F("refresh")] = 10;
|
||||
obj[F("refresh_url")] = "/";
|
||||
obj[F("html")] = F("reboot. Autoreload after 10 seconds");
|
||||
|
@ -282,6 +285,7 @@ class RestApi {
|
|||
obj[F("lat")] = mConfig->sun.lat ? String(mConfig->sun.lat, 5) : "";
|
||||
obj[F("lon")] = mConfig->sun.lat ? String(mConfig->sun.lon, 5) : "";
|
||||
obj[F("disnightcom")] = mConfig->sun.disNightCom;
|
||||
obj[F("offs")] = mConfig->sun.offsetSec;
|
||||
}
|
||||
|
||||
void getPinout(JsonObject obj) {
|
||||
|
@ -343,10 +347,12 @@ class RestApi {
|
|||
|
||||
void getIndex(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getRadio(obj.createNestedObject(F("radio")));
|
||||
getStatistics(obj.createNestedObject(F("statistics")));
|
||||
obj["refresh_interval"] = mConfig->nrf.sendInterval;
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
|
||||
obj[F("ts_now")] = mApp->getTimestamp();
|
||||
obj[F("ts_sunrise")] = mApp->getSunrise();
|
||||
obj[F("ts_sunset")] = mApp->getSunset();
|
||||
obj[F("ts_offset")] = mConfig->sun.offsetSec;
|
||||
|
||||
JsonArray inv = obj.createNestedArray(F("inverter"));
|
||||
Inverter<> *iv;
|
||||
|
@ -369,22 +375,27 @@ class RestApi {
|
|||
if(!mSys->Radio.isChipConnected())
|
||||
warn.add(F("your NRF24 module can't be reached, check the wiring and pinout"));
|
||||
else if(!mSys->Radio.isPVariant())
|
||||
warn.add(F("your NRF24 module isn't a plus version(+), maybe incompatible!"));
|
||||
warn.add(F("your NRF24 module isn't a plus version(+), maybe incompatible"));
|
||||
if(!mApp->getSettingsValid())
|
||||
warn.add(F("your settings are invalid"));
|
||||
if(mApp->getRebootRequestState())
|
||||
warn.add(F("reboot your ESP to apply all your configuration changes"));
|
||||
if(0 == mApp->getTimestamp())
|
||||
warn.add(F("time not set. No communication to inverter possible"));
|
||||
/*if(0 == mSys->getNumInverters())
|
||||
warn.add(F("no inverter configured"));*/
|
||||
|
||||
if((!mApp->getMqttIsConnected()) && (String(mConfig->mqtt.broker).length() > 0))
|
||||
warn.add(F("MQTT is not connected"));
|
||||
|
||||
JsonArray info = obj.createNestedArray(F("infos"));
|
||||
if(mApp->getRebootRequestState())
|
||||
info.add(F("reboot your ESP to apply all your configuration changes!"));
|
||||
if(!mApp->getSettingsValid())
|
||||
info.add(F("your settings are invalid"));
|
||||
if(mApp->getMqttIsConnected())
|
||||
info.add(F("MQTT is connected, ") + String(mApp->getMqttTxCnt()) + F(" packets sent, ") + String(mApp->getMqttRxCnt()) + F(" packets received"));
|
||||
}
|
||||
|
||||
void getSetup(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getInverterList(obj.createNestedObject(F("inverter")));
|
||||
getMqtt(obj.createNestedObject(F("mqtt")));
|
||||
|
@ -402,7 +413,7 @@ class RestApi {
|
|||
|
||||
void getLive(JsonObject obj) {
|
||||
getMenu(obj.createNestedObject(F("menu")));
|
||||
getSysInfo(obj.createNestedObject(F("system")));
|
||||
getGeneric(obj.createNestedObject(F("generic")));
|
||||
JsonArray invArr = obj.createNestedArray(F("inverter"));
|
||||
obj["refresh_interval"] = mConfig->nrf.sendInterval;
|
||||
|
||||
|
|
|
@ -1,4 +1,36 @@
|
|||
/**
|
||||
* SVG ICONS
|
||||
*/
|
||||
|
||||
iconWifi1 = [
|
||||
"M11.046 10.454c.226-.226.185-.605-.1-.75A6.473 6.473 0 0 0 8 9c-1.06 0-2.062.254-2.946.704-.285.145-.326.524-.1.75l.015.015c.16.16.407.19.611.09A5.478 5.478 0 0 1 8 10c.868 0 1.69.201 2.42.56.203.1.45.07.611-.091l.015-.015zM9.06 12.44c.196-.196.198-.52-.04-.66A1.99 1.99 0 0 0 8 11.5a1.99 1.99 0 0 0-1.02.28c-.238.14-.236.464-.04.66l.706.706a.5.5 0 0 0 .707 0l.708-.707z"
|
||||
];
|
||||
|
||||
iconWifi2 = [
|
||||
"M13.229 8.271c.216-.216.194-.578-.063-.745A9.456 9.456 0 0 0 8 6c-1.905 0-3.68.56-5.166 1.526a.48.48 0 0 0-.063.745.525.525 0 0 0 .652.065A8.46 8.46 0 0 1 8 7a8.46 8.46 0 0 1 4.577 1.336c.205.132.48.108.652-.065zm-2.183 2.183c.226-.226.185-.605-.1-.75A6.473 6.473 0 0 0 8 9c-1.06 0-2.062.254-2.946.704-.285.145-.326.524-.1.75l.015.015c.16.16.408.19.611.09A5.478 5.478 0 0 1 8 10c.868 0 1.69.201 2.42.56.203.1.45.07.611-.091l.015-.015zM9.06 12.44c.196-.196.198-.52-.04-.66A1.99 1.99 0 0 0 8 11.5a1.99 1.99 0 0 0-1.02.28c-.238.14-.236.464-.04.66l.706.706a.5.5 0 0 0 .708 0l.707-.707z"
|
||||
];
|
||||
|
||||
iconWifi3 = [
|
||||
"M15.384 6.115a.485.485 0 0 0-.047-.736A12.444 12.444 0 0 0 8 3C5.259 3 2.723 3.882.663 5.379a.485.485 0 0 0-.048.736.518.518 0 0 0 .668.05A11.448 11.448 0 0 1 8 4c2.507 0 4.827.802 6.716 2.164.205.148.49.13.668-.049z",
|
||||
"M13.229 8.271a.482.482 0 0 0-.063-.745A9.455 9.455 0 0 0 8 6c-1.905 0-3.68.56-5.166 1.526a.48.48 0 0 0-.063.745.525.525 0 0 0 .652.065A8.46 8.46 0 0 1 8 7a8.46 8.46 0 0 1 4.576 1.336c.206.132.48.108.653-.065zm-2.183 2.183c.226-.226.185-.605-.1-.75A6.473 6.473 0 0 0 8 9c-1.06 0-2.062.254-2.946.704-.285.145-.326.524-.1.75l.015.015c.16.16.407.19.611.09A5.478 5.478 0 0 1 8 10c.868 0 1.69.201 2.42.56.203.1.45.07.61-.091l.016-.015zM9.06 12.44c.196-.196.198-.52-.04-.66A1.99 1.99 0 0 0 8 11.5a1.99 1.99 0 0 0-1.02.28c-.238.14-.236.464-.04.66l.706.706a.5.5 0 0 0 .707 0l.707-.707z"
|
||||
];
|
||||
|
||||
iconWarn = [
|
||||
"M7.938 2.016A.13.13 0 0 1 8.002 2a.13.13 0 0 1 .063.016.146.146 0 0 1 .054.057l6.857 11.667c.036.06.035.124.002.183a.163.163 0 0 1-.054.06.116.116 0 0 1-.066.017H1.146a.115.115 0 0 1-.066-.017.163.163 0 0 1-.054-.06.176.176 0 0 1 .002-.183L7.884 2.073a.147.147 0 0 1 .054-.057zm1.044-.45a1.13 1.13 0 0 0-1.96 0L.165 13.233c-.457.778.091 1.767.98 1.767h13.713c.889 0 1.438-.99.98-1.767L8.982 1.566z",
|
||||
"M7.002 12a1 1 0 1 1 2 0 1 1 0 0 1-2 0zM7.1 5.995a.905.905 0 1 1 1.8 0l-.35 3.507a.552.552 0 0 1-1.1 0L7.1 5.995z"
|
||||
];
|
||||
|
||||
iconInfo = [
|
||||
"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z",
|
||||
"m8.93 6.588-2.29.287-.082.38.45.083c.294.07.352.176.288.469l-.738 3.468c-.194.897.105 1.319.808 1.319.545 0 1.178-.252 1.465-.598l.088-.416c-.2.176-.492.246-.686.246-.275 0-.375-.193-.304-.533L8.93 6.588zM9 4.5a1 1 0 1 1-2 0 1 1 0 0 1 2 0z"
|
||||
];
|
||||
|
||||
iconSuccess = [
|
||||
"M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z",
|
||||
"M10.97 4.97a.235.235 0 0 0-.02.022L7.477 9.417 5.384 7.323a.75.75 0 0 0-1.06 1.06L6.97 11.03a.75.75 0 0 0 1.079-.02l3.992-4.99a.75.75 0 0 0-1.071-1.05z"
|
||||
];
|
||||
|
||||
/**
|
||||
* GENERIC FUNCTIONS
|
||||
*/
|
||||
|
||||
|
@ -31,6 +63,15 @@ function parseESP(obj) {
|
|||
document.getElementById("esp_type").innerHTML="Board: " + obj["esp_type"];
|
||||
}
|
||||
|
||||
function parseRssi(obj) {
|
||||
var icon = iconWifi3;
|
||||
if(obj["wifi_rssi"] <= -80)
|
||||
icon = iconWifi1;
|
||||
else if(obj["wifi_rssi"] <= -70)
|
||||
icon = iconWifi2;
|
||||
document.getElementById("wifiicon").replaceChildren(svg(icon, 32, 32, "#fff", null, obj["wifi_rssi"]));
|
||||
}
|
||||
|
||||
function setHide(id, hide) {
|
||||
var elm = document.getElementById(id);
|
||||
if(hide) {
|
||||
|
@ -99,15 +140,11 @@ function inp(name, val, max=32, cl=["text"], id=null, type=null) {
|
|||
return e;
|
||||
}
|
||||
|
||||
function sel(name, opt, selId) {
|
||||
function sel(name, options, selId) {
|
||||
e = document.createElement('select');
|
||||
e.name = name;
|
||||
for(it of opt) {
|
||||
o = document.createElement('option');
|
||||
o.value = it[0];
|
||||
o.innerHTML = it[1];
|
||||
if(it[0] == selId)
|
||||
o.selected = true;
|
||||
for(it of options) {
|
||||
o = opt(it[0], it[1], (it[0] == selId));
|
||||
e.appendChild(o);
|
||||
}
|
||||
return e;
|
||||
|
@ -120,11 +157,12 @@ function selDelAllOpt(sel) {
|
|||
}
|
||||
}
|
||||
|
||||
function opt(val, html) {
|
||||
function opt(val, html, sel=false) {
|
||||
o = document.createElement('option');
|
||||
o.value = val;
|
||||
o.innerHTML = html;
|
||||
e.appendChild(o);
|
||||
if(sel)
|
||||
o.selected = true;
|
||||
return o;
|
||||
}
|
||||
|
||||
|
@ -156,3 +194,25 @@ function link(dst, text, target=null) {
|
|||
a.appendChild(t);
|
||||
return a;
|
||||
}
|
||||
|
||||
function svg(data=null, w=24, h=24, color="#000", cl=null, tooltip=null) {
|
||||
var s = document.createElementNS('http://www.w3.org/2000/svg', 'svg');
|
||||
s.setAttribute('width', w);
|
||||
s.setAttribute('height', h);
|
||||
s.setAttribute('fill', color);
|
||||
s.setAttribute('viewBox', '0 0 16 16');
|
||||
if(null != cl) s.setAttribute('class', cl);
|
||||
if(null != data) {
|
||||
for(const e of data) {
|
||||
const i = document.createElementNS('http://www.w3.org/2000/svg', 'path');
|
||||
i.setAttribute('d', e);
|
||||
s.appendChild(i);
|
||||
}
|
||||
}
|
||||
if(null != tooltip) {
|
||||
const t = document.createElement("title");
|
||||
t.appendChild(document.createTextNode(tooltip));
|
||||
s.appendChild(t);
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
|
@ -35,23 +36,18 @@
|
|||
<span class="des">Uptime: </span><span id="uptime"></span><br/>
|
||||
<span class="des">ESP-Time: </span><span id="date"></span>
|
||||
</p>
|
||||
<div id="sun">
|
||||
<span class="des">Communication</span><br/>
|
||||
<span class="des">start: </span><span id="sunrise"></span><br>
|
||||
<span class="des">stop: </span><span id="sunset"></span>
|
||||
</div>
|
||||
<p><span class="des">WiFi RSSI: </span><span id="wifi_rssi"></span> dBm</p>
|
||||
<p>
|
||||
<span class="des">System Infos: </span>
|
||||
<pre id="stat"></pre>
|
||||
<pre id="iv"></pre>
|
||||
<pre id="warn_info"></pre>
|
||||
<span class="des">System Infos:</span>
|
||||
<div id="iv"></div>
|
||||
<div class="hr"></div>
|
||||
<div id="warn_info"></div>
|
||||
</p>
|
||||
|
||||
<div class="hr"></div>
|
||||
<div id="note">
|
||||
Discuss with us on <a href="https://discord.gg/WzhxEY62mB">Discord</a><br/>
|
||||
<h3>Support this project:</h3>
|
||||
<ul>
|
||||
<li>Discuss with us on <a href="https://discord.gg/WzhxEY62mB">Discord</a></li>
|
||||
<li>Report <a href="https://github.com/lumapu/ahoy/issues" target="_blank">issues</a></li>
|
||||
<li>Contribute to <a href="https://github.com/lumapu/ahoy/blob/main/User_Manual.md" target="_blank">documentation</a></li>
|
||||
<li>Test <a href="https://github.com/lumapu/ahoy/actions/workflows/compile_development.yml" target="_blank">development firmware</a></li>
|
||||
|
@ -83,6 +79,7 @@
|
|||
var exeOnce = true;
|
||||
var tickCnt = 0;
|
||||
var ts = 0;
|
||||
var commInfo = "";
|
||||
|
||||
function apiCb(obj) {
|
||||
var e = document.getElementById("apiResult");
|
||||
|
@ -102,24 +99,28 @@
|
|||
getAjax("/api/setup", apiCb, "POST", JSON.stringify(obj));
|
||||
}
|
||||
|
||||
function parseSys(obj) {
|
||||
function ts2Span(ts) {
|
||||
return span(new Date(ts * 1000).toLocaleString('de-DE'));
|
||||
}
|
||||
|
||||
function parseGeneric(obj) {
|
||||
// Disclaimer
|
||||
//if(obj["disclaimer"] == false) sessionStorage.setItem("gDisclaimer", promptFunction());
|
||||
if(exeOnce){
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
}
|
||||
document.getElementById("wifi_rssi").innerHTML = obj["wifi_rssi"];
|
||||
parseRssi(obj);
|
||||
}
|
||||
|
||||
function parseSys(obj) {
|
||||
ts = obj["ts_now"];
|
||||
var date = new Date(obj["ts_now"] * 1000);
|
||||
var up = obj["ts_uptime"];
|
||||
var up = obj["generic"]["ts_uptime"];
|
||||
var days = parseInt(up / 86400) % 365;
|
||||
var hrs = parseInt(up / 3600) % 24;
|
||||
var min = parseInt(up / 60) % 60;
|
||||
var sec = up % 60;
|
||||
var sunrise = new Date(obj["ts_sunrise"] * 1000);
|
||||
var sunset = new Date(obj["ts_sunset"] * 1000);
|
||||
var e = document.getElementById("uptime");
|
||||
e.innerHTML = days + " Day";
|
||||
if(1 != days)
|
||||
|
@ -139,60 +140,73 @@
|
|||
e.addEventListener("click", setTime);
|
||||
}
|
||||
|
||||
if(0 == obj["ts_sunrise"]) {
|
||||
var e = document.getElementById("sun");
|
||||
if(null != e)
|
||||
e.parentNode.removeChild(e);
|
||||
if(obj["ts_sunrise"] > 0) {
|
||||
if(((obj["ts_sunrise"] - obj["ts_offset"]) < obj["ts_now"])
|
||||
&& ((obj["ts_sunset"] + obj["ts_offset"]) > obj["ts_now"])) {
|
||||
commInfo = "Polling inverter(s), will stop at " + (new Date((obj["ts_sunset"] + obj["ts_offset"]) * 1000).toLocaleString('de-DE'));
|
||||
}
|
||||
else {
|
||||
commInfo = "Night time, no Communication to Inverter, ";
|
||||
if(obj["ts_now"] > (obj["ts_sunrise"] - obj["ts_offset"])) {
|
||||
commInfo += "stopped polling at " + (new Date((obj["ts_sunset"] + obj["ts_offset"]) * 1000).toLocaleString('de-DE'));
|
||||
}
|
||||
else {
|
||||
commInfo += "will start polling at " + (new Date((obj["ts_sunrise"] - obj["ts_offset"]) * 1000).toLocaleString('de-DE'));
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
document.getElementById("sunrise").innerHTML = sunrise.toLocaleString('de-DE');
|
||||
document.getElementById("sunset").innerHTML = sunset.toLocaleString('de-DE');
|
||||
}
|
||||
}
|
||||
|
||||
function parseStat(obj) {
|
||||
document.getElementById("stat").innerHTML = "RX success: " + obj["rx_success"]
|
||||
+ "\nRX fail: " + obj["rx_fail"]
|
||||
+ "\nRX no answer: " + obj["rx_fail_answer"]
|
||||
+ "\nFrames received: " + obj["frame_cnt"]
|
||||
+ "\nTX cnt: " + obj["tx_cnt"];
|
||||
}
|
||||
|
||||
function parseIv(obj) {
|
||||
var html = "";
|
||||
var p = div(["none"]);
|
||||
for(var i of obj) {
|
||||
html += "Inverter #" + i["id"] + ": " + i["name"] + " (v" + i["version"] + ") is ";
|
||||
if(false == i["is_avail"])
|
||||
html += "not yet available\n";
|
||||
else {
|
||||
html += "available and is ";
|
||||
if(false == i["is_producing"])
|
||||
html += "not ";
|
||||
html += "producing\n";
|
||||
var icon = iconWarn;
|
||||
var color = "#F70";
|
||||
avail = "";
|
||||
if(false == i["enabled"]) {
|
||||
avail = "disabled";
|
||||
}
|
||||
else if(false == i["is_avail"]) {
|
||||
icon = iconInfo;
|
||||
color = "#00d";
|
||||
avail = "not yet available";
|
||||
}
|
||||
else {
|
||||
icon = iconSuccess;
|
||||
avail = "available and is ";
|
||||
if(false == i["is_producing"])
|
||||
avail += "not ";
|
||||
avail += "producing";
|
||||
}
|
||||
|
||||
p.append(
|
||||
svg(icon, 20, 20, color, "icon"),
|
||||
span("Inverter #" + i["id"] + ": " + i["name"] + " (v" + i["version"] + ") is " + avail),
|
||||
br()
|
||||
);
|
||||
|
||||
if(false == i["is_avail"]) {
|
||||
if(i["ts_last_success"] > 0) {
|
||||
var date = new Date(i["ts_last_success"] * 1000);
|
||||
html += "-> last successful transmission: " + date.toLocaleString('de-DE') + "\n";
|
||||
p.append(span("-> last successful transmission: " + date.toLocaleString('de-DE')), br());
|
||||
}
|
||||
}
|
||||
if(false == i["enabled"])
|
||||
html += "-> disabled\n";
|
||||
|
||||
}
|
||||
document.getElementById("iv").innerHTML = html;
|
||||
document.getElementById("iv").replaceChildren(p);
|
||||
}
|
||||
|
||||
function parseWarnInfo(warn, info) {
|
||||
var html = "";
|
||||
function parseWarnInfo(warn, success) {
|
||||
var p = div(["none"]);
|
||||
for(var w of warn) {
|
||||
html += "WARN: " + w + "\n";
|
||||
p.append(svg(iconWarn, 20, 20, "#F70", "icon"), span(w), br());
|
||||
}
|
||||
for(var i of info) {
|
||||
html += "INFO: " + i + "\n";
|
||||
for(var i of success) {
|
||||
p.append(svg(iconSuccess, 20, 20, "#090", "icon"), span(i), br());
|
||||
}
|
||||
document.getElementById("warn_info").innerHTML = html;
|
||||
|
||||
if(commInfo.length > 0)
|
||||
p.append(svg(iconInfo, 20, 20, "#00d", "icon"), span(commInfo), br());
|
||||
document.getElementById("warn_info").replaceChildren(p);
|
||||
}
|
||||
|
||||
function tick() {
|
||||
|
@ -208,8 +222,8 @@
|
|||
if(null != obj) {
|
||||
if(exeOnce)
|
||||
parseMenu(obj["menu"]);
|
||||
parseSys(obj["system"]);
|
||||
parseStat(obj["statistics"]);
|
||||
parseGeneric(obj["generic"]);
|
||||
parseSys(obj);
|
||||
parseIv(obj["inverter"]);
|
||||
parseWarnInfo(obj["warnings"], obj["infos"]);
|
||||
if(exeOnce) {
|
||||
|
@ -217,8 +231,6 @@
|
|||
exeOnce = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
document.getElementById("refresh").innerHTML = "n/a";
|
||||
}
|
||||
|
||||
getAjax("/api/index", parse);
|
||||
|
|
|
@ -33,10 +33,10 @@
|
|||
</div>
|
||||
<script type="text/javascript">
|
||||
function parse(obj) {
|
||||
parseVersion(obj["system"]);
|
||||
parseVersion(obj["general"]);
|
||||
}
|
||||
|
||||
getAjax("/api/index", parse);
|
||||
getAjax("/api/generic", parse);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
|
@ -83,7 +84,7 @@
|
|||
var con = document.getElementById("serial");
|
||||
var exeOnce = true;
|
||||
|
||||
function parseSys(obj) {
|
||||
function parseGeneric(obj) {
|
||||
var up = obj["ts_uptime"];
|
||||
var days = parseInt(up / 86400) % 365;
|
||||
var hrs = parseInt(up / 3600) % 24;
|
||||
|
@ -94,10 +95,11 @@
|
|||
+ ("0"+min).substr(-2) + ":"
|
||||
+ ("0"+sec).substr(-2);
|
||||
|
||||
parseRssi(obj);
|
||||
if(true == exeOnce) {
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
window.setInterval("getAjax('/api/system', parseSys)", 10000);
|
||||
window.setInterval("getAjax('/api/generic', parseGeneric)", 10000);
|
||||
exeOnce = false;
|
||||
getAjax("/api/setup", parse);
|
||||
}
|
||||
|
@ -201,7 +203,7 @@
|
|||
getAjax("/api/ctrl", ctrlCb, "POST", JSON.stringify(obj));
|
||||
});
|
||||
|
||||
getAjax("/api/system", parseSys);
|
||||
getAjax("/api/generic", parseGeneric);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
|
@ -41,7 +42,7 @@
|
|||
<input type="hidden" name="disclaimer" value="false" id="disclaimer">
|
||||
</fieldset>
|
||||
|
||||
<button type="button" class="s_collapsible">WiFi</button>
|
||||
<button type="button" class="s_collapsible">Network</button>
|
||||
<div class="s_content">
|
||||
<fieldset>
|
||||
<legend class="des">WiFi</legend>
|
||||
|
@ -116,6 +117,8 @@
|
|||
<input type="text" class="text" name="sunLat"/>
|
||||
<label for="sunLon">Longitude (decimal)</label>
|
||||
<input type="text" class="text" name="sunLon"/>
|
||||
<label for="sunOffs">Offset (pre sunrise, post sunset)</label>
|
||||
<select name="sunOffs"></select>
|
||||
<br>
|
||||
<label for="sunDisNightCom">disable night communication</label>
|
||||
<input type="checkbox" class="cb" name="sunDisNightCom"/><br/>
|
||||
|
@ -337,8 +340,12 @@
|
|||
var e = document.getElementsByName("adminpwd")[0];
|
||||
if(!obj["pwd_set"])
|
||||
e.value = "";
|
||||
}
|
||||
|
||||
function parseGeneric(obj) {
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
parseRssi(obj);
|
||||
}
|
||||
|
||||
function parseStaticIp(obj) {
|
||||
|
@ -368,6 +375,10 @@
|
|||
document.getElementsByName("sunLat")[0].value = obj["lat"];
|
||||
document.getElementsByName("sunLon")[0].value = obj["lon"];
|
||||
document.getElementsByName("sunDisNightCom")[0].checked = obj["disnightcom"];
|
||||
const sel = document.getElementsByName("sunOffs")[0];
|
||||
for(var i = 0; i <= 60; i++) {
|
||||
sel.appendChild(opt(i, i + " minutes", (i == (obj["offs"] / 60))));
|
||||
}
|
||||
}
|
||||
|
||||
function parsePinout(obj, type) {
|
||||
|
@ -452,6 +463,7 @@
|
|||
if(null != root) {
|
||||
parseMenu(root["menu"]);
|
||||
parseSys(root["system"]);
|
||||
parseGeneric(root["generic"]);
|
||||
parseStaticIp(root["static_ip"]);
|
||||
parseIv(root["inverter"]);
|
||||
parseMqtt(root["mqtt"]);
|
||||
|
|
|
@ -31,11 +31,11 @@ h2 {
|
|||
}
|
||||
|
||||
.topnav a.icon {
|
||||
top: 0;
|
||||
left: 0;
|
||||
background: #333;
|
||||
display: block;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
}
|
||||
|
||||
.topnav a:hover {
|
||||
|
@ -43,6 +43,20 @@ h2 {
|
|||
color: #000;
|
||||
}
|
||||
|
||||
.topnav .info {
|
||||
color: #fff;
|
||||
position: absolute;
|
||||
right: 24px;
|
||||
top: 5px;
|
||||
}
|
||||
|
||||
svg.icon {
|
||||
vertical-align: middle;
|
||||
display: inline-block;
|
||||
margin-top:-4x;
|
||||
padding: 5px 7px 5px 0px;
|
||||
}
|
||||
|
||||
.title {
|
||||
background-color: #006ec0;
|
||||
color: #fff !important;
|
||||
|
@ -142,6 +156,13 @@ span.seperator {
|
|||
display: block;
|
||||
}
|
||||
|
||||
.topnav .info {
|
||||
top: auto !important;
|
||||
right: auto !important;
|
||||
bottom: 14px;
|
||||
left: 24px;
|
||||
}
|
||||
|
||||
#content {
|
||||
padding: 15px 15px 120px 250px;
|
||||
}
|
||||
|
@ -376,11 +397,16 @@ div.ModPwr, div.ModName {
|
|||
display: inline-block;
|
||||
}
|
||||
|
||||
div.hr {
|
||||
height: 1px;
|
||||
border-top: 1px solid #ccc;
|
||||
margin: 10px 0px 10px;
|
||||
}
|
||||
|
||||
#note {
|
||||
margin: 50px 10px 10px 10px;
|
||||
margin: 10px 10px 10px 10px;
|
||||
padding-top: 10px;
|
||||
width: 100%;
|
||||
border-top: 1px solid #bbb;
|
||||
}
|
||||
|
||||
@media(max-width: 500px) {
|
||||
|
@ -477,6 +503,12 @@ div.ModPwr, div.ModName {
|
|||
.mt-4 { margin-top: 1.5rem }
|
||||
.mt-5 { margin-top: 3rem }
|
||||
|
||||
.mb-1 { margin-bottom: 0.25rem }
|
||||
.mb-2 { margin-bottom: 0.5rem }
|
||||
.mb-3 { margin-bottom: 1rem }
|
||||
.mb-4 { margin-bottom: 1.5rem }
|
||||
.mb-5 { margin-bottom: 3rem }
|
||||
|
||||
.a-r { text-align: right; }
|
||||
.a-c { text-align: center; }
|
||||
|
||||
|
|
|
@ -15,12 +15,15 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
<pre id="stat"></pre>
|
||||
<div id="info" class="col-sm-12 col-md-6 mt-3"></div>
|
||||
<div id="radio" class="col-sm-12 col-md-6 mt-3"></div>
|
||||
<div id="system" class="mt-3"></div>
|
||||
<div id="sun" class="col-sm-12 col-md-6 mt-3"></div>
|
||||
<div id="html" class="mt-3 mb-3"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div id="footer">
|
||||
|
@ -40,9 +43,10 @@
|
|||
</div>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
function parseSys(obj) {
|
||||
function parseGeneric(obj) {
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
parseRssi(obj);
|
||||
}
|
||||
|
||||
function genTabRow(key, value) {
|
||||
|
@ -54,7 +58,7 @@
|
|||
|
||||
function parseSysInfo(obj) {
|
||||
const data = ["sdk", "cpu_freq", "chip_revision",
|
||||
"chip_model", "chip_cores", "esp_type", "mac", "wifi_rssi",
|
||||
"chip_model", "chip_cores", "esp_type", "mac", "wifi_rssi", "ts_uptime",
|
||||
"flash_size", "sketch_used", "heap_total", "heap_free", "heap_frag",
|
||||
"max_free_blk", "version", "core_version", "reboot_reason"];
|
||||
|
||||
|
@ -71,7 +75,7 @@
|
|||
}
|
||||
}
|
||||
|
||||
function parseRadio(obj) {
|
||||
function parseRadio(obj, stat) {
|
||||
const pa = ["MIN", "LOW", "HIGH", "MAX"];
|
||||
const datarate = ["1 MBps", "2 MBps", "250 kbps"];
|
||||
|
||||
|
@ -88,12 +92,35 @@
|
|||
main.appendChild(genTabRow("Datarate", datarate[obj["DataRate"]]));
|
||||
main.appendChild(genTabRow("Power Level", pa[obj["power_level"]]));
|
||||
}
|
||||
|
||||
main.append(
|
||||
genTabRow("RX success", stat["rx_success"]),
|
||||
genTabRow("RX fail", stat["rx_fail"]),
|
||||
genTabRow("RX no answer", stat["rx_fail_answer"]),
|
||||
genTabRow("RX frames received", stat["frame_cnt"]),
|
||||
genTabRow("TX count", stat["tx_cnt"])
|
||||
);
|
||||
}
|
||||
|
||||
function parseIndex(obj) {
|
||||
var h = div(["head", "p-2"]);
|
||||
var r = div(["row"]);
|
||||
r.appendChild(div(["col", "a-c"], "Sun"));
|
||||
h.appendChild(r);
|
||||
|
||||
document.getElementById("sun").append (
|
||||
h,
|
||||
genTabRow("Sunrise", new Date(obj["ts_sunrise"] * 1000).toLocaleString('de-DE')),
|
||||
genTabRow("Sunset", new Date(obj["ts_sunset"] * 1000).toLocaleString('de-DE')),
|
||||
genTabRow("Communication start", new Date((obj["ts_sunrise"] - obj["ts_offset"]) * 1000).toLocaleString('de-DE')),
|
||||
genTabRow("Communication stop", new Date((obj["ts_sunset"] + obj["ts_offset"]) * 1000).toLocaleString('de-DE'))
|
||||
);
|
||||
}
|
||||
|
||||
function parse(obj) {
|
||||
if(null != obj) {
|
||||
parseMenu(obj["menu"]);
|
||||
parseSys(obj["system"]);
|
||||
parseGeneric(obj["generic"]);
|
||||
|
||||
if(null != obj["refresh"]) {
|
||||
var meta = document.createElement('meta');
|
||||
|
@ -103,10 +130,10 @@
|
|||
}
|
||||
else {
|
||||
parseSysInfo(obj["system"]);
|
||||
parseRadio(obj["system"]["radio"]);
|
||||
parseRadio(obj["system"]["radio"], obj["system"]["statistics"]);
|
||||
getAjax('/api/index', parseIndex);
|
||||
}
|
||||
var e = document.getElementById("system");
|
||||
e.innerHTML = obj["html"];
|
||||
document.getElementById("html").innerHTML = obj["html"];
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
|
@ -40,15 +41,16 @@
|
|||
</div>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
function parseSys(obj) {
|
||||
function parseGeneric(obj) {
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
parseRssi(obj);
|
||||
}
|
||||
|
||||
function parse(obj) {
|
||||
if(null != obj) {
|
||||
parseMenu(obj["menu"]);
|
||||
parseSys(obj["system"]);
|
||||
parseGeneric(obj["generic"]);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
<span></span>
|
||||
</a>
|
||||
<div id="topnav" class="hide"></div>
|
||||
<div id="wifiicon" class="info"></div>
|
||||
</div>
|
||||
<div id="wrapper">
|
||||
<div id="content">
|
||||
|
@ -42,11 +43,12 @@
|
|||
<script type="text/javascript">
|
||||
var exeOnce = true;
|
||||
|
||||
function parseSys(obj) {
|
||||
function parseGeneric(obj) {
|
||||
if(true == exeOnce){
|
||||
parseVersion(obj);
|
||||
parseESP(obj);
|
||||
}
|
||||
parseRssi(obj);
|
||||
}
|
||||
|
||||
function parseIv(obj, root) {
|
||||
|
@ -117,7 +119,7 @@
|
|||
if(obj.length > 1) {
|
||||
for(var j = 0; j < root.ch0_fld_names.length; j++) {
|
||||
var val = Math.round(total[j] * 100) / 100;
|
||||
if(val > 0) {
|
||||
if((j == 2) || (j == 6) || (j == 7) || (j == 8) || (j == 10)) {
|
||||
var sub = div(["subgrp"]);
|
||||
sub.appendChild(span(val + " " + span(root["ch0_fld_units"][j], ["unit"]).innerHTML, ["value"]));
|
||||
sub.appendChild(span(root["ch0_fld_names"][j], ["info"]));
|
||||
|
@ -133,7 +135,7 @@
|
|||
if(null != obj) {
|
||||
if(true == exeOnce)
|
||||
parseMenu(obj["menu"]);
|
||||
parseSys(obj["system"]);
|
||||
parseGeneric(obj["generic"]);
|
||||
parseIv(obj["inverter"], obj);
|
||||
document.getElementById("refresh").innerHTML = obj["refresh_interval"];
|
||||
if(true == exeOnce) {
|
||||
|
|
|
@ -463,10 +463,12 @@ class Web {
|
|||
mConfig->sun.lat = 0.0;
|
||||
mConfig->sun.lon = 0.0;
|
||||
mConfig->sun.disNightCom = false;
|
||||
mConfig->sun.offsetSec = 0;
|
||||
} else {
|
||||
mConfig->sun.lat = request->arg("sunLat").toFloat();
|
||||
mConfig->sun.lon = request->arg("sunLon").toFloat();
|
||||
mConfig->sun.disNightCom = (request->arg("sunDisNightCom") == "on");
|
||||
mConfig->sun.offsetSec = request->arg("sunOffs").toInt() * 60;
|
||||
}
|
||||
|
||||
// mqtt
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue