");
- } else {
+ }
+ else
+ {
modHtml += F(" W");
}
uint8_t list[] = {FLD_UAC, FLD_IAC, FLD_PAC, FLD_F, FLD_PCT, FLD_T, FLD_YT, FLD_YD, FLD_PDC, FLD_EFF, FLD_PRA, FLD_ALARM_MES_ID};
- for(uint8_t fld = 0; fld < 12; fld++) {
+ for (uint8_t fld = 0; fld < 12; fld++)
+ {
pos = (iv->getPosByChFld(CH0, list[fld]));
- if(0xff != pos) {
+ if (0xff != pos)
+ {
modHtml += F("
";
- for(uint8_t ch = 1; ch <= modNum; ch ++) {
+ for (uint8_t ch = 1; ch <= modNum; ch++)
+ {
modHtml += F("
");
- if(iv->chName[ch-1][0] == 0)
+ if (iv->chName[ch - 1][0] == 0)
modHtml += F("CHANNEL ") + String(ch);
else
- modHtml += String(iv->chName[ch-1]);
+ modHtml += String(iv->chName[ch - 1]);
modHtml += F("");
- for(uint8_t j = 0; j < 6; j++) {
- switch(j) {
- default: pos = (iv->getPosByChFld(ch, FLD_UDC)); break;
- case 1: pos = (iv->getPosByChFld(ch, FLD_IDC)); break;
- case 2: pos = (iv->getPosByChFld(ch, FLD_PDC)); break;
- case 3: pos = (iv->getPosByChFld(ch, FLD_YD)); break;
- case 4: pos = (iv->getPosByChFld(ch, FLD_YT)); break;
- case 5: pos = (iv->getPosByChFld(ch, FLD_IRR)); break;
+ for (uint8_t j = 0; j < 6; j++)
+ {
+ switch (j)
+ {
+ default:
+ pos = (iv->getPosByChFld(ch, FLD_UDC));
+ break;
+ case 1:
+ pos = (iv->getPosByChFld(ch, FLD_IDC));
+ break;
+ case 2:
+ pos = (iv->getPosByChFld(ch, FLD_PDC));
+ break;
+ case 3:
+ pos = (iv->getPosByChFld(ch, FLD_YD));
+ break;
+ case 4:
+ pos = (iv->getPosByChFld(ch, FLD_YT));
+ break;
+ case 5:
+ pos = (iv->getPosByChFld(ch, FLD_IRR));
+ break;
}
- if(0xff != pos) {
+ if (0xff != pos)
+ {
modHtml += F("
") + String(iv->getValue(pos));
modHtml += F("") + String(iv->getUnit(pos)) + F("");
modHtml += F("
") + String(iv->getFieldName(pos)) + F("");
@@ -626,7 +623,8 @@ String app::getLiveData(void) {
// dump all data to web frontend
modHtml = F("
");
char topic[30], val[10];
- for(uint8_t i = 0; i < iv->listLen; i++) {
+ for (uint8_t i = 0; i < iv->listLen; i++)
+ {
snprintf(topic, 30, "%s/ch%d/%s", iv->name, iv->assign[i].ch, iv->getFieldName(i));
snprintf(val, 10, "%.3f %s", iv->getValue(i), iv->getUnit(i));
modHtml += String(topic) + ": " + String(val) + "\n";
@@ -638,7 +636,6 @@ String app::getLiveData(void) {
return modHtml;
}
-
//-----------------------------------------------------------------------------
String app::getJson(void) {
DPRINTLN(DBG_VERBOSE, F("app::showJson"));
diff --git a/tools/esp8266/defines.h b/tools/esp8266/defines.h
index a0e3ac08..31b65b77 100644
--- a/tools/esp8266/defines.h
+++ b/tools/esp8266/defines.h
@@ -25,22 +25,22 @@ typedef struct {
typedef enum {
InverterDevInform_Simple = 0, // 0x00
InverterDevInform_All = 1, // 0x01
- //GridOnProFilePara = 2, // 0x02
- //HardWareConfig = 3, // 0x03
- //SimpleCalibrationPara = 4, // 0x04
- //SystemConfigPara = 5, // 0x05
+ GridOnProFilePara = 2, // 0x02
+ HardWareConfig = 3, // 0x03
+ SimpleCalibrationPara = 4, // 0x04
+ SystemConfigPara = 5, // 0x05
RealTimeRunData_Debug = 11, // 0x0b
- //RealTimeRunData_Reality = 12, // 0x0c
- //RealTimeRunData_A_Phase = 13, // 0x0d
- //RealTimeRunData_B_Phase = 14, // 0x0e
- //RealTimeRunData_C_Phase = 15, // 0x0f
+ RealTimeRunData_Reality = 12, // 0x0c
+ RealTimeRunData_A_Phase = 13, // 0x0d
+ RealTimeRunData_B_Phase = 14, // 0x0e
+ RealTimeRunData_C_Phase = 15, // 0x0f
AlarmData = 17, // 0x11, Alarm data - all unsent alarms
AlarmUpdate = 18, // 0x12, Alarm data - all pending alarms
- //RecordData = 19, // 0x13
- //InternalData = 20, // 0x14
+ RecordData = 19, // 0x13
+ InternalData = 20, // 0x14
GetLossRate = 21, // 0x15
- //GetSelfCheckState = 30, // 0x1e
- //InitDataState = 0xff
+ GetSelfCheckState = 30, // 0x1e
+ InitDataState = 0xff
} InfoCmdType;
typedef enum {
diff --git a/tools/esp8266/hmDefines.h b/tools/esp8266/hmDefines.h
index e69bc071..36139bb2 100644
--- a/tools/esp8266/hmDefines.h
+++ b/tools/esp8266/hmDefines.h
@@ -23,9 +23,9 @@ const char* const units[] = {"V", "A", "W", "Wh", "kWh", "Hz", "°C", "%","VAr",
// field types
enum {FLD_UDC = 0, FLD_IDC, FLD_PDC, FLD_YD, FLD_YW, FLD_YT,
- FLD_UAC, FLD_IAC, FLD_PAC, FLD_F, FLD_T, FLD_PCT, FLD_EFF, FLD_IRR, FLD_PRA,FLD_ALARM_MES_ID,FLD_FW_VERSION,FLD_FW_BUILD_YEAR,FLD_FW_BUILD_MONTH_DAY,FLD_HW_ID};
+ FLD_UAC, FLD_IAC, FLD_PAC, FLD_F, FLD_T, FLD_PCT, FLD_EFF, FLD_IRR, FLD_PRA,FLD_ALARM_MES_ID,FLD_FW_VERSION,FLD_FW_BUILD_YEAR,FLD_FW_BUILD_MONTH_DAY,FLD_HW_ID,FLD_ACT_PWR_LIMIT};
const char* const fields[] = {"U_DC", "I_DC", "P_DC", "YieldDay", "YieldWeek", "YieldTotal",
- "U_AC", "I_AC", "P_AC", "Freq", "Temp", "Pct", "Efficiency", "Irradiation","P_ACr","ALARM_MES_ID","FWVersion","FWBuildYear","FWBuildMonthDay","HWPartId"};
+ "U_AC", "I_AC", "P_AC", "Freq", "Temp", "Pct", "Efficiency", "Irradiation","P_ACr","ALARM_MES_ID","FWVersion","FWBuildYear","FWBuildMonthDay","HWPartId","PowerLimit"};
// mqtt discovery device classes
enum {DEVICE_CLS_NONE = 0, DEVICE_CLS_CURRENT, DEVICE_CLS_ENERGY, DEVICE_CLS_PWR, DEVICE_CLS_VOLTAGE, DEVICE_CLS_FREQ, DEVICE_CLS_TEMP};
@@ -92,6 +92,12 @@ const byteAssign_t InfoAssignment[] = {
};
#define HMINFO_LIST_LEN (sizeof(InfoAssignment) / sizeof(byteAssign_t))
+const byteAssign_t SystemConfigParaAssignment[] = {
+ { FLD_ACT_PWR_LIMIT, UNIT_PCT, CH0, 2, 2, 10 }
+};
+#define HMSYSTEM_LIST_LEN (sizeof(SystemConfigParaAssignment) / sizeof(byteAssign_t))
+
+
//-------------------------------------
diff --git a/tools/esp8266/hmInverter.h b/tools/esp8266/hmInverter.h
index be67bc9d..774fd809 100644
--- a/tools/esp8266/hmInverter.h
+++ b/tools/esp8266/hmInverter.h
@@ -12,6 +12,8 @@
#endif
#include "hmDefines.h"
+#include
+#include
/**
* For values which are of interest and not transmitted by the inverter can be
@@ -51,8 +53,34 @@ template
struct calcFunc_t {
uint8_t funcId; // unique id
func_t* func; // function pointer
-} ;
+};
+
+
+class CommandAbstract {
+ public:
+ CommandAbstract(uint8_t txType = 0, uint8_t cmd = 0){
+ _TxType = txType;
+ _Cmd = cmd;
+ };
+ virtual ~CommandAbstract() {};
+
+ const uint8_t getCmd()
+ {
+ return _Cmd;
+ }
+
+ protected:
+ uint8_t _TxType;
+ uint8_t _Cmd;
+};
+class InfoCommand : public CommandAbstract {
+public:
+ InfoCommand(uint8_t cmd){
+ _TxType = 0x15;
+ _Cmd = cmd;
+ }
+};
// list of all available functions, mapped in hmDefines.h
template
@@ -77,6 +105,7 @@ class Inverter {
uint16_t alarmMesIndex; // Last recorded Alarm Message Index
uint16_t fwVersion; // Firmware Version from Info Command Request
uint16_t powerLimit[2]; // limit power output
+ uint16_t actPowerLimit; //
uint8_t devControlCmd; // carries the requested cmd
bool devControlRequest; // true if change needed
serial_u serial; // serial number as on barcode
@@ -92,6 +121,7 @@ class Inverter {
ts = 0;
powerLimit[0] = 0xffff; // 65535 W Limit -> unlimited
powerLimit[1] = 0x0000; //
+ actPowerLimit = 0xffff; // init feedback from inverter to -1
devControlRequest = false;
devControlCmd = 0xff;
initialized = false;
@@ -102,6 +132,30 @@ class Inverter {
// TODO: cleanup
}
+ template
+ void enqueCommand(uint8_t cmd)
+ {
+ _commandQueue.push(std::make_shared(cmd));
+ DPRINTLN(DBG_INFO, "enqueuedCmd: " + String(cmd));
+ }
+
+ void setQueuedCmdFinished(){
+ if (!_commandQueue.empty()){
+ _commandQueue.pop(); // Will destroy CommandAbstract Class Object (?)
+ }
+ }
+
+ uint8_t getQueuedCmd()
+ {
+ if (_commandQueue.empty()){
+ // Fill with default commands
+ enqueCommand(RealTimeRunData_Debug);
+ //enqueCommand(SystemConfigPara);
+ }
+ return _commandQueue.front().get()->getCmd();
+ }
+
+
void init(void) {
DPRINTLN(DBG_VERBOSE, F("hmInverter.h:init"));
getAssignment();
@@ -110,6 +164,8 @@ class Inverter {
memset(name, 0, MAX_NAME_LENGTH);
memset(chName, 0, MAX_NAME_LENGTH * 4);
memset(record, 0, sizeof(RECORDTYPE) * listLen);
+ enqueCommand(InverterDevInform_All);
+ enqueCommand(SystemConfigPara);
initialized = true;
}
@@ -138,8 +194,9 @@ class Inverter {
return assign[pos].ch;
}
- void addValue(uint8_t pos, uint8_t buf[],uint8_t cmd) {
+ void addValue(uint8_t pos, uint8_t buf[]) {
DPRINTLN(DBG_VERBOSE, F("hmInverter.h:addValue"));
+ uint8_t cmd = getQueuedCmd();
uint8_t ptr = assign[pos].start;
uint8_t end = ptr + assign[pos].num;
uint16_t div = assign[pos].div;
@@ -149,8 +206,7 @@ class Inverter {
val <<= 8;
val |= buf[ptr];
} while(++ptr != end);
-
- record[pos] = (RECORDTYPE)(val) / (RECORDTYPE)(div);
+ record[pos] = (RECORDTYPE)(val) / (RECORDTYPE)(div);
}
if (cmd == RealTimeRunData_Debug) {
// get last alarm message index and save it in the inverter object
@@ -165,6 +221,13 @@ class Inverter {
DPRINT(DBG_DEBUG, F("Inverter FW-Version: ") + String(fwVersion));
}
}
+ if (cmd == SystemConfigPara) {
+ // get at least the firmware version and save it to the inverter object
+ if (getPosByChFld(0, FLD_ACT_PWR_LIMIT) == pos){
+ actPowerLimit = record[pos];
+ DPRINT(DBG_DEBUG, F("Inverter actual power limit: ") + String(actPowerLimit));
+ }
+ }
}
RECORDTYPE getValue(uint8_t pos) {
@@ -172,9 +235,10 @@ class Inverter {
return record[pos];
}
- void doCalculations(uint8_t cmd=RealTimeRunData_Debug) {
+ void doCalculations() {
DPRINTLN(DBG_VERBOSE, F("hmInverter.h:doCalculations"));
- getAssignment(cmd);
+ uint8_t cmd = getQueuedCmd();
+ getAssignment();
if (cmd == RealTimeRunData_Debug){
for(uint8_t i = 0; i < listLen; i++) {
if(CMD_CALC == assign[i].div) {
@@ -204,37 +268,52 @@ class Inverter {
return ts;
}
- void getAssignment(uint8_t cmd=RealTimeRunData_Debug) {
- DPRINTLN(DBG_VERBOSE, F("hmInverter.h:getAssignment"));
- if(cmd == RealTimeRunData_Debug){
- if(INV_TYPE_1CH == type) {
- listLen = (uint8_t)(HM1CH_LIST_LEN);
- assign = (byteAssign_t*)hm1chAssignment;
+ void getAssignment() {
+ DPRINTLN(DBG_DEBUG, F("hmInverter.h:getAssignment"));
+ uint8_t cmd = getQueuedCmd();
+ switch (cmd)
+ {
+ case RealTimeRunData_Debug:
+ if (INV_TYPE_1CH == type)
+ {
+ listLen = (uint8_t)(HM1CH_LIST_LEN);
+ assign = (byteAssign_t *)hm1chAssignment;
channels = 1;
}
- else if(INV_TYPE_2CH == type) {
- listLen = (uint8_t)(HM2CH_LIST_LEN);
- assign = (byteAssign_t*)hm2chAssignment;
+ else if (INV_TYPE_2CH == type)
+ {
+ listLen = (uint8_t)(HM2CH_LIST_LEN);
+ assign = (byteAssign_t *)hm2chAssignment;
channels = 2;
}
- else if(INV_TYPE_4CH == type) {
- listLen = (uint8_t)(HM4CH_LIST_LEN);
- assign = (byteAssign_t*)hm4chAssignment;
+ else if (INV_TYPE_4CH == type)
+ {
+ listLen = (uint8_t)(HM4CH_LIST_LEN);
+ assign = (byteAssign_t *)hm4chAssignment;
channels = 4;
}
- else {
- listLen = 0;
+ else
+ {
+ listLen = 0;
channels = 0;
- assign = NULL;
+ assign = NULL;
}
- }
- if(cmd == InverterDevInform_All){
- listLen = (uint8_t)(HMINFO_LIST_LEN);
- assign = (byteAssign_t*)InfoAssignment;
+ break;
+ case InverterDevInform_All:
+ listLen = (uint8_t)(HMINFO_LIST_LEN);
+ assign = (byteAssign_t *)InfoAssignment;
+ break;
+ case SystemConfigPara:
+ listLen = (uint8_t)(HMSYSTEM_LIST_LEN);
+ assign = (byteAssign_t *)SystemConfigParaAssignment;
+ break;
+ default:
+ DPRINTLN(DBG_INFO, "Parser not implemented");
}
}
private:
+ std::queue> _commandQueue;
void toRadioId(void) {
DPRINTLN(DBG_VERBOSE, F("hmInverter.h:toRadioId"));
radioId.u64 = 0ULL;
diff --git a/tools/esp8266/hmSystem.h b/tools/esp8266/hmSystem.h
index 00f2c381..aa9c7645 100644
--- a/tools/esp8266/hmSystem.h
+++ b/tools/esp8266/hmSystem.h
@@ -19,13 +19,10 @@ class HmSystem {
RadioType Radio;
typedef BUFFER BufferType;
BufferType BufCtrl;
- InfoCmdType NextInfoCmd; // For cmd-queue FIFO with one place
- InfoCmdType InfoCmd; // For cmd-queue FIFO with one place
//DevControlCmdType DevControlCmd;
HmSystem() {
mNumInv = 0;
- InfoCmd = RealTimeRunData_Debug; // default case
}
~HmSystem() {
// TODO: cleanup
diff --git a/tools/esp8266/html/h/index_html.h b/tools/esp8266/html/h/index_html.h
index 2e55a2a2..c6f769ce 100644
--- a/tools/esp8266/html/h/index_html.h
+++ b/tools/esp8266/html/h/index_html.h
@@ -1,4 +1,4 @@
#ifndef __INDEX_HTML_H__
#define __INDEX_HTML_H__
-const char index_html[] PROGMEM = "Index - {DEVICE}AHOY - {DEVICE}
Visualization
Setup
Uptime:
Statistics:
Every {TS}seconds the values are updated
";
+const char index_html[] PROGMEM = "Index - {DEVICE}AHOY - {DEVICE}
Visualization
Setup
Uptime:
Statistics:
Every {TS}seconds the values are updated
";
#endif /*__INDEX_HTML_H__*/
diff --git a/tools/esp8266/html/index.html b/tools/esp8266/html/index.html
index 850c0579..de381281 100644
--- a/tools/esp8266/html/index.html
+++ b/tools/esp8266/html/index.html
@@ -5,11 +5,6 @@