mirror of
https://github.com/emsesp/EMS-ESP32.git
synced 2025-12-06 07:49:52 +03:00
add SM10 solar values and commands
This commit is contained in:
@@ -58,6 +58,7 @@ void WebSettings::read(WebSettings & settings, JsonObject & root) {
|
|||||||
root["notoken_api"] = settings.notoken_api;
|
root["notoken_api"] = settings.notoken_api;
|
||||||
root["analog_enabled"] = settings.analog_enabled;
|
root["analog_enabled"] = settings.analog_enabled;
|
||||||
root["pbutton_gpio"] = settings.pbutton_gpio;
|
root["pbutton_gpio"] = settings.pbutton_gpio;
|
||||||
|
root["solar_maxflow"] = settings.solar_maxflow;
|
||||||
root["board_profile"] = settings.board_profile;
|
root["board_profile"] = settings.board_profile;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -169,7 +170,8 @@ StateUpdateResult WebSettings::update(JsonObject & root, WebSettings & settings)
|
|||||||
settings.master_thermostat = root["master_thermostat"] | EMSESP_DEFAULT_MASTER_THERMOSTAT;
|
settings.master_thermostat = root["master_thermostat"] | EMSESP_DEFAULT_MASTER_THERMOSTAT;
|
||||||
|
|
||||||
// doesn't need any follow-up actions
|
// doesn't need any follow-up actions
|
||||||
settings.notoken_api = root["notoken_api"] | EMSESP_DEFAULT_NOTOKEN_API;
|
settings.notoken_api = root["notoken_api"] | EMSESP_DEFAULT_NOTOKEN_API;
|
||||||
|
settings.solar_maxflow = root["solar_maxflow"] | EMSESP_DEFAULT_SOLAR_MAXFLOW;
|
||||||
|
|
||||||
return StateUpdateResult::CHANGED;
|
return StateUpdateResult::CHANGED;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -53,6 +53,7 @@ class WebSettings {
|
|||||||
bool notoken_api;
|
bool notoken_api;
|
||||||
bool analog_enabled;
|
bool analog_enabled;
|
||||||
uint8_t pbutton_gpio;
|
uint8_t pbutton_gpio;
|
||||||
|
uint8_t solar_maxflow;
|
||||||
String board_profile;
|
String board_profile;
|
||||||
|
|
||||||
static void read(WebSettings & settings, JsonObject & root);
|
static void read(WebSettings & settings, JsonObject & root);
|
||||||
|
|||||||
@@ -152,4 +152,8 @@
|
|||||||
#define EMSESP_DEFAULT_SUBSCRIBE_FORMAT 0
|
#define EMSESP_DEFAULT_SUBSCRIBE_FORMAT 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifndef EMSESP_DEFAULT_SOLAR_MAXFLOW
|
||||||
|
#define EMSESP_DEFAULT_SOLAR_MAXFLOW 30
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -30,7 +30,9 @@ Solar::Solar(uint8_t device_type, uint8_t device_id, uint8_t product_id, const s
|
|||||||
|
|
||||||
// telegram handlers
|
// telegram handlers
|
||||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
register_telegram_type(0x0097, F("SM10Monitor"), true, MAKE_PF_CB(process_SM10Monitor));
|
register_telegram_type(0x97, F("SM10Monitor"), false, MAKE_PF_CB(process_SM10Monitor));
|
||||||
|
register_telegram_type(0x96, F("SM10Config"), true, MAKE_PF_CB(process_SM10Config));
|
||||||
|
EMSESP::send_read_request(0x97, device_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM100) {
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM100) {
|
||||||
@@ -55,7 +57,7 @@ Solar::Solar(uint8_t device_type, uint8_t device_id, uint8_t product_id, const s
|
|||||||
|
|
||||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_ISM) {
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_ISM) {
|
||||||
register_telegram_type(0x0103, F("ISM1StatusMessage"), true, MAKE_PF_CB(process_ISM1StatusMessage));
|
register_telegram_type(0x0103, F("ISM1StatusMessage"), true, MAKE_PF_CB(process_ISM1StatusMessage));
|
||||||
register_telegram_type(0x0101, F("ISM1Set"), false, MAKE_PF_CB(process_ISM1Set));
|
register_telegram_type(0x0101, F("ISM1Set"), true, MAKE_PF_CB(process_ISM1Set));
|
||||||
}
|
}
|
||||||
|
|
||||||
// device values...
|
// device values...
|
||||||
@@ -78,24 +80,47 @@ Solar::Solar(uint8_t device_type, uint8_t device_id, uint8_t product_id, const s
|
|||||||
|
|
||||||
register_device_value(TAG_NONE, &collectorTemp_, DeviceValueType::SHORT, FL_(div10), FL_(collectorTemp), DeviceValueUOM::DEGREES);
|
register_device_value(TAG_NONE, &collectorTemp_, DeviceValueType::SHORT, FL_(div10), FL_(collectorTemp), DeviceValueUOM::DEGREES);
|
||||||
register_device_value(TAG_NONE, &tankBottomTemp_, DeviceValueType::SHORT, FL_(div10), FL_(tankBottomTemp), DeviceValueUOM::DEGREES);
|
register_device_value(TAG_NONE, &tankBottomTemp_, DeviceValueType::SHORT, FL_(div10), FL_(tankBottomTemp), DeviceValueUOM::DEGREES);
|
||||||
register_device_value(TAG_NONE, &tankBottomTemp2_, DeviceValueType::SHORT, FL_(div10), FL_(tank2BottomTemp), DeviceValueUOM::DEGREES);
|
|
||||||
register_device_value(TAG_NONE, &heatExchangerTemp_, DeviceValueType::SHORT, FL_(div10), FL_(heatExchangerTemp), DeviceValueUOM::DEGREES);
|
|
||||||
|
|
||||||
register_device_value(
|
|
||||||
TAG_NONE, &tankBottomMaxTemp_, DeviceValueType::UINT, nullptr, FL_(tankMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_SM100TankBottomMaxTemp));
|
|
||||||
register_device_value(TAG_NONE, &solarPumpModulation_, DeviceValueType::UINT, nullptr, FL_(solarPumpModulation), DeviceValueUOM::PERCENT);
|
|
||||||
register_device_value(TAG_NONE, &cylinderPumpModulation_, DeviceValueType::UINT, nullptr, FL_(cylinderPumpModulation), DeviceValueUOM::PERCENT);
|
|
||||||
|
|
||||||
register_device_value(TAG_NONE, &solarPump_, DeviceValueType::BOOL, nullptr, FL_(solarPump), DeviceValueUOM::PUMP);
|
register_device_value(TAG_NONE, &solarPump_, DeviceValueType::BOOL, nullptr, FL_(solarPump), DeviceValueUOM::PUMP);
|
||||||
register_device_value(TAG_NONE, &valveStatus_, DeviceValueType::BOOL, nullptr, FL_(valveStatus), DeviceValueUOM::NONE);
|
|
||||||
register_device_value(TAG_NONE, &tankHeated_, DeviceValueType::BOOL, nullptr, FL_(tankHeated), DeviceValueUOM::NONE);
|
|
||||||
register_device_value(TAG_NONE, &collectorShutdown_, DeviceValueType::BOOL, nullptr, FL_(collectorShutdown), DeviceValueUOM::NONE);
|
|
||||||
|
|
||||||
register_device_value(TAG_NONE, &pumpWorkTime_, DeviceValueType::TIME, nullptr, FL_(pumpWorkTime), DeviceValueUOM::MINUTES);
|
register_device_value(TAG_NONE, &pumpWorkTime_, DeviceValueType::TIME, nullptr, FL_(pumpWorkTime), DeviceValueUOM::MINUTES);
|
||||||
|
register_device_value(TAG_NONE, &tankMaxTemp_, DeviceValueType::UINT, nullptr, FL_(tankMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_TankMaxTemp));
|
||||||
|
|
||||||
register_device_value(TAG_NONE, &energyLastHour_, DeviceValueType::ULONG, FL_(div10), FL_(energyLastHour), DeviceValueUOM::WH);
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
register_device_value(TAG_NONE, &energyTotal_, DeviceValueType::ULONG, FL_(div10), FL_(energyTotal), DeviceValueUOM::KWH);
|
// register_device_value(TAG_NONE, &collectorMaxTemp_, DeviceValueType::UINT, nullptr, FL_(collectorMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_CollectorMaxTemp));
|
||||||
register_device_value(TAG_NONE, &energyToday_, DeviceValueType::ULONG, nullptr, FL_(energyToday), DeviceValueUOM::WH);
|
register_device_value(TAG_NONE, &solarPumpModulation_, DeviceValueType::UINT, nullptr, FL_(solarPumpModulation), DeviceValueUOM::PERCENT);
|
||||||
|
register_device_value(TAG_NONE, &solarPumpMinMod_, DeviceValueType::UINT, nullptr, FL_(pumpMinMod), DeviceValueUOM::PERCENT, MAKE_CF_CB(set_PumpMinMod));
|
||||||
|
register_device_value(TAG_NONE, &solarPumpTurnonDiff_, DeviceValueType::UINT, nullptr, FL_(solarPumpTurnonDiff), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_TurnonDiff));
|
||||||
|
register_device_value(TAG_NONE, &solarPumpTurnoffDiff_, DeviceValueType::UINT, nullptr, FL_(solarPumpTurnoffDiff), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_TurnoffDiff));
|
||||||
|
register_device_value(TAG_NONE, &collectorMaxTemp_, DeviceValueType::UINT, nullptr, FL_(collectorMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_CollectorMaxTemp));
|
||||||
|
register_device_value(TAG_NONE, &collectorMinTemp_, DeviceValueType::UINT, nullptr, FL_(collectorMinTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_CollectorMinTemp));
|
||||||
|
register_device_value(TAG_NONE, &collectorShutdown_, DeviceValueType::BOOL, nullptr, FL_(collectorShutdown), DeviceValueUOM::NONE);
|
||||||
|
// register_device_value(TAG_NONE, &tankHeated_, DeviceValueType::BOOL, nullptr, FL_(tankHeated), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &solarPower_, DeviceValueType::ULONG, nullptr, FL_(solarPower), DeviceValueUOM::W);
|
||||||
|
register_device_value(TAG_NONE, &energyLastHour_, DeviceValueType::ULONG, FL_(div10), FL_(energyLastHour), DeviceValueUOM::WH);
|
||||||
|
register_device_value(TAG_NONE, &maxFlow_, DeviceValueType::UINT, FL_(div10), FL_(maxFlow), DeviceValueUOM::LMIN, MAKE_CF_CB(set_SM10MaxFlow));
|
||||||
|
register_device_value(TAG_DEVICE_DATA_WW, &wwMinTemp_, DeviceValueType::UINT, nullptr, FL_(wwMinTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwMinTemp));
|
||||||
|
}
|
||||||
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_ISM) {
|
||||||
|
register_device_value(TAG_NONE, &collectorShutdown_, DeviceValueType::BOOL, nullptr, FL_(collectorShutdown), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &tankHeated_, DeviceValueType::BOOL, nullptr, FL_(tankHeated), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &energyLastHour_, DeviceValueType::ULONG, FL_(div10), FL_(energyLastHour), DeviceValueUOM::WH);
|
||||||
|
}
|
||||||
|
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM100) {
|
||||||
|
register_device_value(TAG_NONE, &solarPumpModulation_, DeviceValueType::UINT, nullptr, FL_(solarPumpModulation), DeviceValueUOM::PERCENT);
|
||||||
|
register_device_value(TAG_NONE, &solarPumpMinMod_, DeviceValueType::UINT, nullptr, FL_(pumpMinMod), DeviceValueUOM::PERCENT, MAKE_CF_CB(set_PumpMinMod));
|
||||||
|
register_device_value(TAG_NONE, &solarPumpTurnonDiff_, DeviceValueType::UINT, nullptr, FL_(solarPumpTurnonDiff), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_TurnonDiff));
|
||||||
|
register_device_value(TAG_NONE, &solarPumpTurnoffDiff_, DeviceValueType::UINT, nullptr, FL_(solarPumpTurnoffDiff), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_TurnoffDiff));
|
||||||
|
register_device_value(TAG_NONE, &tankBottomTemp2_, DeviceValueType::SHORT, FL_(div10), FL_(tank2BottomTemp), DeviceValueUOM::DEGREES);
|
||||||
|
register_device_value(TAG_NONE, &heatExchangerTemp_, DeviceValueType::SHORT, FL_(div10), FL_(heatExchangerTemp), DeviceValueUOM::DEGREES);
|
||||||
|
register_device_value(TAG_NONE, &cylinderPumpModulation_, DeviceValueType::UINT, nullptr, FL_(cylinderPumpModulation), DeviceValueUOM::PERCENT);
|
||||||
|
register_device_value(TAG_NONE, &valveStatus_, DeviceValueType::BOOL, nullptr, FL_(valveStatus), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &tankHeated_, DeviceValueType::BOOL, nullptr, FL_(tankHeated), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &collectorShutdown_, DeviceValueType::BOOL, nullptr, FL_(collectorShutdown), DeviceValueUOM::NONE);
|
||||||
|
register_device_value(TAG_NONE, &collectorMaxTemp_, DeviceValueType::UINT, nullptr, FL_(collectorMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_CollectorMaxTemp));
|
||||||
|
register_device_value(TAG_NONE, &collectorMinTemp_, DeviceValueType::UINT, nullptr, FL_(collectorMinTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_CollectorMinTemp));
|
||||||
|
register_device_value(TAG_NONE, &energyLastHour_, DeviceValueType::ULONG, FL_(div10), FL_(energyLastHour), DeviceValueUOM::WH);
|
||||||
|
register_device_value(TAG_NONE, &energyToday_, DeviceValueType::ULONG, nullptr, FL_(energyToday), DeviceValueUOM::WH);
|
||||||
|
register_device_value(TAG_NONE, &energyTotal_, DeviceValueType::ULONG, FL_(div10), FL_(energyTotal), DeviceValueUOM::KWH);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// publish HA config
|
// publish HA config
|
||||||
@@ -124,13 +149,60 @@ bool Solar::publish_ha_config() {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SM10Monitor - type 0x96
|
||||||
|
// Solar(0x30) -> All(0x00), (0x96), data: FF 18 19 0A 02 5A 27 0A 05 2D 1E 0F 64 28 0A
|
||||||
|
void Solar::process_SM10Config(std::shared_ptr<const Telegram> telegram) {
|
||||||
|
uint8_t colmax = collectorMaxTemp_ / 10;
|
||||||
|
has_update(telegram->read_value(colmax, 3));
|
||||||
|
collectorMaxTemp_ = colmax * 10;
|
||||||
|
uint8_t colmin = collectorMinTemp_ / 10;
|
||||||
|
has_update(telegram->read_value(colmin, 4));
|
||||||
|
collectorMinTemp_ = colmin * 10;
|
||||||
|
has_update(telegram->read_value(solarPumpMinMod_, 2));
|
||||||
|
has_update(telegram->read_value(solarPumpTurnonDiff_, 7));
|
||||||
|
has_update(telegram->read_value(solarPumpTurnoffDiff_, 8));
|
||||||
|
has_update(telegram->read_value(tankMaxTemp_, 5));
|
||||||
|
has_update(telegram->read_value(wwMinTemp_, 6));
|
||||||
|
}
|
||||||
|
|
||||||
// SM10Monitor - type 0x97
|
// SM10Monitor - type 0x97
|
||||||
void Solar::process_SM10Monitor(std::shared_ptr<const Telegram> telegram) {
|
void Solar::process_SM10Monitor(std::shared_ptr<const Telegram> telegram) {
|
||||||
|
uint8_t solarpumpmod = solarPumpModulation_;
|
||||||
|
|
||||||
|
has_update(telegram->read_bitvalue(collectorShutdown_, 0, 3));
|
||||||
|
// has_update(telegram->read_bitvalue(tankHeated_, 0, x)); // tank full, to be determined
|
||||||
has_update(telegram->read_value(collectorTemp_, 2)); // collector temp from SM10, is *10
|
has_update(telegram->read_value(collectorTemp_, 2)); // collector temp from SM10, is *10
|
||||||
has_update(telegram->read_value(tankBottomTemp_, 5)); // tank bottom temp from SM10, is *10
|
has_update(telegram->read_value(tankBottomTemp_, 5)); // tank bottom temp from SM10, is *10
|
||||||
has_update(telegram->read_value(solarPumpModulation_, 4)); // modulation solar pump
|
has_update(telegram->read_value(solarPumpModulation_, 4)); // modulation solar pump
|
||||||
has_update(telegram->read_bitvalue(solarPump_, 7, 1));
|
has_update(telegram->read_bitvalue(solarPump_, 7, 1));
|
||||||
has_update(telegram->read_value(pumpWorkTime_, 8, 3));
|
has_update(telegram->read_value(pumpWorkTime_, 8, 3));
|
||||||
|
|
||||||
|
// mask out pump-boosts
|
||||||
|
if (solarpumpmod == 0 && solarPumpModulation_ == 100) {
|
||||||
|
solarPumpModulation_ = solarPumpMinMod_; // set to minimum
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!Helpers::hasValue(maxFlow_)) {
|
||||||
|
EMSESP::webSettingsService.read([&](WebSettings & settings) {
|
||||||
|
maxFlow_ = settings.solar_maxflow;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// solar publishes every minute, do not count reads by other devices
|
||||||
|
if (telegram->dest == 0) {
|
||||||
|
// water 4.184 J/gK, glycol ~2.6-2.8 J/gK, no aceotrope
|
||||||
|
// solarPower_ = (collectorTemp_ - tankBottomTemp_) * solarPumpModulation_ * maxFlow_ * 10 / 1434; // water
|
||||||
|
solarPower_ = (collectorTemp_ - tankBottomTemp_) * solarPumpModulation_ * maxFlow_ * 10 / 1665; //40% glycol@40°C
|
||||||
|
if (energy.size() >= 60) {
|
||||||
|
energy.pop_front();
|
||||||
|
}
|
||||||
|
energy.push_back(solarPower_);
|
||||||
|
uint32_t sum = 0;
|
||||||
|
for (auto e : energy) {
|
||||||
|
sum += e;
|
||||||
|
}
|
||||||
|
energyLastHour_ = sum / 6; // counts in 0.1 Wh
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -151,10 +223,10 @@ void Solar::process_SM100SystemConfig(std::shared_ptr<const Telegram> telegram)
|
|||||||
*/
|
*/
|
||||||
void Solar::process_SM100SolarCircuitConfig(std::shared_ptr<const Telegram> telegram) {
|
void Solar::process_SM100SolarCircuitConfig(std::shared_ptr<const Telegram> telegram) {
|
||||||
has_update(telegram->read_value(collectorMaxTemp_, 0, 1));
|
has_update(telegram->read_value(collectorMaxTemp_, 0, 1));
|
||||||
has_update(telegram->read_value(tankBottomMaxTemp_, 3, 1));
|
has_update(telegram->read_value(tankMaxTemp_, 3, 1));
|
||||||
has_update(telegram->read_value(collectorMinTemp_, 4, 1));
|
has_update(telegram->read_value(collectorMinTemp_, 4, 1));
|
||||||
has_update(telegram->read_value(solarPumpMode_, 5, 1));
|
has_update(telegram->read_value(solarPumpMode_, 5, 1));
|
||||||
has_update(telegram->read_value(solarPumpMinRPM_, 6, 1));
|
has_update(telegram->read_value(solarPumpMinMod_, 6, 1));
|
||||||
has_update(telegram->read_value(solarPumpTurnoffDiff_, 7, 1));
|
has_update(telegram->read_value(solarPumpTurnoffDiff_, 7, 1));
|
||||||
has_update(telegram->read_value(solarPumpTurnonDiff_, 8, 1));
|
has_update(telegram->read_value(solarPumpTurnonDiff_, 8, 1));
|
||||||
has_update(telegram->read_value(solarPumpKick_, 9, 1));
|
has_update(telegram->read_value(solarPumpKick_, 9, 1));
|
||||||
@@ -263,11 +335,11 @@ void Solar::process_SM100Status(std::shared_ptr<const Telegram> telegram) {
|
|||||||
has_update(telegram->read_value(solarPumpModulation_, 9));
|
has_update(telegram->read_value(solarPumpModulation_, 9));
|
||||||
|
|
||||||
if (solarpumpmod == 0 && solarPumpModulation_ == 100) { // mask out boosts
|
if (solarpumpmod == 0 && solarPumpModulation_ == 100) { // mask out boosts
|
||||||
solarPumpModulation_ = 15; // set to minimum
|
solarPumpModulation_ = solarPumpMinMod_; // set to minimum
|
||||||
}
|
}
|
||||||
|
|
||||||
if (cylinderpumpmod == 0 && cylinderPumpModulation_ == 100) { // mask out boosts
|
if (cylinderpumpmod == 0 && cylinderPumpModulation_ == 100) { // mask out boosts
|
||||||
cylinderPumpModulation_ = 15; // set to minimum
|
cylinderPumpModulation_ = solarPumpMinMod_; // set to minimum
|
||||||
}
|
}
|
||||||
has_update(telegram->read_bitvalue(tankHeated_, 3, 1)); // issue #422
|
has_update(telegram->read_bitvalue(tankHeated_, 3, 1)); // issue #422
|
||||||
has_update(telegram->read_bitvalue(collectorShutdown_, 3, 0)); // collector shutdown
|
has_update(telegram->read_bitvalue(collectorShutdown_, 3, 0)); // collector shutdown
|
||||||
@@ -318,12 +390,9 @@ void Solar::process_SM100Time(std::shared_ptr<const Telegram> telegram) {
|
|||||||
void Solar::process_ISM1StatusMessage(std::shared_ptr<const Telegram> telegram) {
|
void Solar::process_ISM1StatusMessage(std::shared_ptr<const Telegram> telegram) {
|
||||||
has_update(telegram->read_value(collectorTemp_, 4)); // Collector Temperature
|
has_update(telegram->read_value(collectorTemp_, 4)); // Collector Temperature
|
||||||
has_update(telegram->read_value(tankBottomTemp_, 6)); // Temperature Bottom of Solar Boiler tank
|
has_update(telegram->read_value(tankBottomTemp_, 6)); // Temperature Bottom of Solar Boiler tank
|
||||||
uint16_t Wh = 0xFFFF;
|
uint16_t Wh = energyLastHour_ / 10;
|
||||||
has_update(telegram->read_value(Wh, 2)); // Solar Energy produced in last hour only ushort, is not * 10
|
has_update(telegram->read_value(Wh, 2)); // Solar Energy produced in last hour only ushort, is not * 10
|
||||||
|
energyLastHour_ = Wh * 10; // set to *10
|
||||||
if (Wh != 0xFFFF) {
|
|
||||||
energyLastHour_ = Wh * 10; // set to *10
|
|
||||||
}
|
|
||||||
|
|
||||||
has_update(telegram->read_bitvalue(solarPump_, 8, 0)); // PS1 Solar pump on (1) or off (0)
|
has_update(telegram->read_bitvalue(solarPump_, 8, 0)); // PS1 Solar pump on (1) or off (0)
|
||||||
has_update(telegram->read_value(pumpWorkTime_, 10, 3)); // force to 3 bytes
|
has_update(telegram->read_value(pumpWorkTime_, 10, 3)); // force to 3 bytes
|
||||||
@@ -335,21 +404,111 @@ void Solar::process_ISM1StatusMessage(std::shared_ptr<const Telegram> telegram)
|
|||||||
* Junkers ISM1 Solar Module - type 0x0101 EMS+ for setting values
|
* Junkers ISM1 Solar Module - type 0x0101 EMS+ for setting values
|
||||||
*/
|
*/
|
||||||
void Solar::process_ISM1Set(std::shared_ptr<const Telegram> telegram) {
|
void Solar::process_ISM1Set(std::shared_ptr<const Telegram> telegram) {
|
||||||
has_update(telegram->read_value(setpoint_maxBottomTemp_, 6));
|
has_update(telegram->read_value(tankMaxTemp_, 6));
|
||||||
}
|
}
|
||||||
|
|
||||||
// set temperature for tank
|
/*
|
||||||
bool Solar::set_SM100TankBottomMaxTemp(const char * value, const int8_t id) {
|
* Settings
|
||||||
|
*/
|
||||||
|
// collector shutdown temperature
|
||||||
|
bool Solar::set_CollectorMaxTemp(const char * value, const int8_t id) {
|
||||||
int temperature;
|
int temperature;
|
||||||
if (!Helpers::value2number(value, temperature)) {
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
if (flags() == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
|
write_command(0x96, 3, (uint8_t)temperature / 10, 0x96);
|
||||||
|
} else {
|
||||||
|
write_command(0x35A, 0, (uint8_t)temperature, 0x35A);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// write value
|
// collector shutdown temperature
|
||||||
// 90 30 FF 03 02 5A 59 B3
|
bool Solar::set_CollectorMinTemp(const char * value, const int8_t id) {
|
||||||
// note: optionally add the validate to 0x035A which will pick up the adjusted tank1MaxTempCurrent_
|
int temperature;
|
||||||
write_command(0x35A, 0x03, (uint8_t)temperature);
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (flags() == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
|
write_command(0x96, 4, (uint8_t)temperature / 10, 0x96);
|
||||||
|
} else {
|
||||||
|
write_command(0x35A, 4, (uint8_t)temperature, 0x35A);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Solar::set_TankMaxTemp(const char * value, const int8_t id) {
|
||||||
|
int temperature;
|
||||||
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (flags() == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
|
write_command(0x96, 5, (uint8_t)temperature, 0x96);
|
||||||
|
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_ISM) {
|
||||||
|
write_command(0x101, 6, (uint8_t)temperature, 0x101);
|
||||||
|
} else {
|
||||||
|
// write value: 90 30 FF 03 02 5A 59 B3
|
||||||
|
write_command(0x35A, 3, (uint8_t)temperature, 0x35A);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
bool Solar::set_PumpMinMod(const char * value, const int8_t id) {
|
||||||
|
int modulation;
|
||||||
|
if (!Helpers::value2number(value, modulation)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
write_command(0x96, 2, (uint8_t)modulation, 0x96);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Solar::set_wwMinTemp(const char * value, const int8_t id) {
|
||||||
|
int temperature;
|
||||||
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
write_command(0x96, 6, (uint8_t)temperature, 0x96);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Solar::set_TurnoffDiff(const char * value, const int8_t id){
|
||||||
|
int temperature;
|
||||||
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (flags() == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
|
write_command(0x96, 8, (uint8_t)temperature, 0x96);
|
||||||
|
} else {
|
||||||
|
write_command(0x35A, 7, (uint8_t)temperature, 0x35A);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Solar::set_TurnonDiff(const char * value, const int8_t id){
|
||||||
|
int temperature;
|
||||||
|
if (!Helpers::value2number(value, temperature)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (flags() == EMSdevice::EMS_DEVICE_FLAG_SM10) {
|
||||||
|
write_command(0x96, 7, (uint8_t)temperature, 0x96);
|
||||||
|
} else {
|
||||||
|
write_command(0x35A, 8, (uint8_t)temperature, 0x35A);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// external value to calculate energy
|
||||||
|
bool Solar::set_SM10MaxFlow(const char * value, const int8_t id) {
|
||||||
|
float flow;
|
||||||
|
if (!Helpers::value2float(value, flow)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
maxFlow_ = (flow * 10);
|
||||||
|
EMSESP::webSettingsService.update([&](WebSettings & settings) {
|
||||||
|
settings.solar_maxflow = maxFlow_;
|
||||||
|
return StateUpdateResult::CHANGED;
|
||||||
|
}, "local");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -40,7 +40,6 @@ class Solar : public EMSdevice {
|
|||||||
uint8_t cylinderPumpModulation_; // PS5: modulation cylinder pump
|
uint8_t cylinderPumpModulation_; // PS5: modulation cylinder pump
|
||||||
uint8_t solarPump_; // PS1: solar pump active
|
uint8_t solarPump_; // PS1: solar pump active
|
||||||
uint8_t valveStatus_; // VS2: status 3-way valve for cylinder 2 (solar thermal system) with valve
|
uint8_t valveStatus_; // VS2: status 3-way valve for cylinder 2 (solar thermal system) with valve
|
||||||
int16_t setpoint_maxBottomTemp_; // setpoint for maximum collector temp
|
|
||||||
uint32_t energyLastHour_;
|
uint32_t energyLastHour_;
|
||||||
uint32_t energyToday_;
|
uint32_t energyToday_;
|
||||||
uint32_t energyTotal_;
|
uint32_t energyTotal_;
|
||||||
@@ -61,10 +60,10 @@ class Solar : public EMSdevice {
|
|||||||
|
|
||||||
// telegram 0x035A
|
// telegram 0x035A
|
||||||
uint8_t collectorMaxTemp_; // maximum allowed collectorTemp array 1
|
uint8_t collectorMaxTemp_; // maximum allowed collectorTemp array 1
|
||||||
uint8_t tankBottomMaxTemp_; // Current value for max tank temp
|
uint8_t tankMaxTemp_; // Current value for max tank temp
|
||||||
uint8_t collectorMinTemp_; // minimum allowed collectorTemp array 1
|
uint8_t collectorMinTemp_; // minimum allowed collectorTemp array 1
|
||||||
uint8_t solarPumpMode_; // 00=off, 01=PWM, 02=10V
|
uint8_t solarPumpMode_; // 00=off, 01=PWM, 02=10V
|
||||||
uint8_t solarPumpMinRPM_; // minimum RPM setting, *5 %
|
uint8_t solarPumpMinMod_; // minimum modulation setting, *5 %
|
||||||
uint8_t solarPumpTurnoffDiff_; // solar pump turnoff collector/tank diff
|
uint8_t solarPumpTurnoffDiff_; // solar pump turnoff collector/tank diff
|
||||||
uint8_t solarPumpTurnonDiff_; // solar pump turnon collector/tank diff
|
uint8_t solarPumpTurnonDiff_; // solar pump turnon collector/tank diff
|
||||||
uint8_t solarPumpKick_; // pump kick for vacuum collector, 00=off
|
uint8_t solarPumpKick_; // pump kick for vacuum collector, 00=off
|
||||||
@@ -86,10 +85,18 @@ class Solar : public EMSdevice {
|
|||||||
// SM100wwStatus - 0x07AA
|
// SM100wwStatus - 0x07AA
|
||||||
uint8_t wwPump_;
|
uint8_t wwPump_;
|
||||||
|
|
||||||
|
// SM10Config - 0x96
|
||||||
|
uint8_t wwMinTemp_;
|
||||||
|
uint8_t maxFlow_; // set this to caltulate power
|
||||||
|
uint32_t solarPower_; // calculated from maxFlow
|
||||||
|
|
||||||
|
std::deque<uint16_t> energy;
|
||||||
|
|
||||||
char type_[20]; // Solar of WWC
|
char type_[20]; // Solar of WWC
|
||||||
uint8_t id_;
|
uint8_t id_;
|
||||||
|
|
||||||
void process_SM10Monitor(std::shared_ptr<const Telegram> telegram);
|
void process_SM10Monitor(std::shared_ptr<const Telegram> telegram);
|
||||||
|
void process_SM10Config(std::shared_ptr<const Telegram> telegram);
|
||||||
void process_SM100SystemConfig(std::shared_ptr<const Telegram> telegram);
|
void process_SM100SystemConfig(std::shared_ptr<const Telegram> telegram);
|
||||||
void process_SM100SolarCircuitConfig(std::shared_ptr<const Telegram> telegram);
|
void process_SM100SolarCircuitConfig(std::shared_ptr<const Telegram> telegram);
|
||||||
void process_SM100ParamCfg(std::shared_ptr<const Telegram> telegram);
|
void process_SM100ParamCfg(std::shared_ptr<const Telegram> telegram);
|
||||||
@@ -112,7 +119,15 @@ class Solar : public EMSdevice {
|
|||||||
void process_ISM1Set(std::shared_ptr<const Telegram> telegram);
|
void process_ISM1Set(std::shared_ptr<const Telegram> telegram);
|
||||||
|
|
||||||
|
|
||||||
bool set_SM100TankBottomMaxTemp(const char * value, const int8_t id);
|
bool set_CollectorMaxTemp(const char * value, const int8_t id);
|
||||||
|
bool set_CollectorMinTemp(const char * value, const int8_t id);
|
||||||
|
bool set_TankMaxTemp(const char * value, const int8_t id);
|
||||||
|
bool set_PumpMinMod(const char * value, const int8_t id);
|
||||||
|
bool set_wwMinTemp(const char * value, const int8_t id);
|
||||||
|
bool set_TurnonDiff(const char * value, const int8_t id);
|
||||||
|
bool set_TurnoffDiff(const char * value, const int8_t id);
|
||||||
|
|
||||||
|
bool set_SM10MaxFlow(const char * value, const int8_t id);
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace emsesp
|
} // namespace emsesp
|
||||||
|
|||||||
@@ -34,7 +34,8 @@ static const __FlashStringHelper * DeviceValueUOM_s[] __attribute__((__aligned__
|
|||||||
F_(minutes),
|
F_(minutes),
|
||||||
F_(ua),
|
F_(ua),
|
||||||
F_(bar),
|
F_(bar),
|
||||||
F_(kw)
|
F_(kw),
|
||||||
|
F_(w)
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -57,7 +57,7 @@ enum DeviceValueType : uint8_t {
|
|||||||
// Unit Of Measurement mapping - maps to DeviceValueUOM_s in emsdevice.cpp
|
// Unit Of Measurement mapping - maps to DeviceValueUOM_s in emsdevice.cpp
|
||||||
// uom - also used with HA
|
// uom - also used with HA
|
||||||
// sequence is important!
|
// sequence is important!
|
||||||
enum DeviceValueUOM : uint8_t { NONE = 0, DEGREES, PERCENT, LMIN, KWH, WH, HOURS, MINUTES, UA, BAR, KW, PUMP };
|
enum DeviceValueUOM : uint8_t { NONE = 0, DEGREES, PERCENT, LMIN, KWH, WH, HOURS, MINUTES, UA, BAR, KW, W, PUMP };
|
||||||
|
|
||||||
// TAG mapping - maps to DeviceValueTAG_s in emsdevice.cpp
|
// TAG mapping - maps to DeviceValueTAG_s in emsdevice.cpp
|
||||||
enum DeviceValueTAG : uint8_t {
|
enum DeviceValueTAG : uint8_t {
|
||||||
|
|||||||
@@ -80,6 +80,7 @@ MAKE_PSTR_WORD(command)
|
|||||||
MAKE_PSTR_WORD(commands)
|
MAKE_PSTR_WORD(commands)
|
||||||
MAKE_PSTR_WORD(info)
|
MAKE_PSTR_WORD(info)
|
||||||
MAKE_PSTR_WORD(settings)
|
MAKE_PSTR_WORD(settings)
|
||||||
|
MAKE_PSTR_WORD(value)
|
||||||
|
|
||||||
// devices
|
// devices
|
||||||
MAKE_PSTR_WORD(boiler)
|
MAKE_PSTR_WORD(boiler)
|
||||||
@@ -94,6 +95,7 @@ MAKE_PSTR_WORD(heatpump)
|
|||||||
MAKE_PSTR_WORD(generic)
|
MAKE_PSTR_WORD(generic)
|
||||||
MAKE_PSTR_WORD(dallassensor)
|
MAKE_PSTR_WORD(dallassensor)
|
||||||
MAKE_PSTR_WORD(unknown)
|
MAKE_PSTR_WORD(unknown)
|
||||||
|
MAKE_PSTR_WORD(Dallassensor)
|
||||||
|
|
||||||
// format strings
|
// format strings
|
||||||
MAKE_PSTR(EMSESP, "EMS-ESP")
|
MAKE_PSTR(EMSESP, "EMS-ESP")
|
||||||
@@ -165,6 +167,7 @@ MAKE_PSTR(hours, "hours")
|
|||||||
MAKE_PSTR(ua, "uA")
|
MAKE_PSTR(ua, "uA")
|
||||||
MAKE_PSTR(lmin, "l/min")
|
MAKE_PSTR(lmin, "l/min")
|
||||||
MAKE_PSTR(kw, "kW")
|
MAKE_PSTR(kw, "kW")
|
||||||
|
MAKE_PSTR(w, "W")
|
||||||
|
|
||||||
// TAG mapping - maps to DeviceValueTAG_s in emsdevice.cpp
|
// TAG mapping - maps to DeviceValueTAG_s in emsdevice.cpp
|
||||||
// use empty string if want to suppress showing tags
|
// use empty string if want to suppress showing tags
|
||||||
@@ -329,6 +332,9 @@ MAKE_PSTR_LIST(enum_control, F_(off), F_(rc20), F_(rc3x))
|
|||||||
|
|
||||||
MAKE_PSTR_LIST(enum_hamode, F_(off), F_(heat), F_(auto), F_(heat), F_(off), F_(heat), F_(auto), F_(auto), F_(auto), F_(auto))
|
MAKE_PSTR_LIST(enum_hamode, F_(off), F_(heat), F_(auto), F_(heat), F_(off), F_(heat), F_(auto), F_(auto), F_(auto), F_(auto))
|
||||||
|
|
||||||
|
// solar list
|
||||||
|
MAKE_PSTR_LIST(enum_solarmode, F_(constant), F("pwm"), F("analog"))
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* MQTT topics and full text for values and commands
|
* MQTT topics and full text for values and commands
|
||||||
*/
|
*/
|
||||||
@@ -360,7 +366,7 @@ MAKE_PSTR_LIST(curFlowTemp, F("curflowtemp"), F("current flow temperature"))
|
|||||||
MAKE_PSTR_LIST(retTemp, F("rettemp"), F("return temperature"))
|
MAKE_PSTR_LIST(retTemp, F("rettemp"), F("return temperature"))
|
||||||
MAKE_PSTR_LIST(switchTemp, F("switchtemp"), F("mixing switch temperature"))
|
MAKE_PSTR_LIST(switchTemp, F("switchtemp"), F("mixing switch temperature"))
|
||||||
MAKE_PSTR_LIST(sysPress, F("syspress"), F("system pressure"))
|
MAKE_PSTR_LIST(sysPress, F("syspress"), F("system pressure"))
|
||||||
MAKE_PSTR_LIST(boilTemp, F("boiltemp"), F("max boiler temperature"))
|
MAKE_PSTR_LIST(boilTemp, F("boiltemp"), F("boiler temperature"))
|
||||||
MAKE_PSTR_LIST(exhaustTemp, F("exhausttemp"), F("exhaust temperature"))
|
MAKE_PSTR_LIST(exhaustTemp, F("exhausttemp"), F("exhaust temperature"))
|
||||||
MAKE_PSTR_LIST(burnGas, F("burngas"), F("gas"))
|
MAKE_PSTR_LIST(burnGas, F("burngas"), F("gas"))
|
||||||
MAKE_PSTR_LIST(flameCurr, F("flamecurr"), F("flame current"))
|
MAKE_PSTR_LIST(flameCurr, F("flamecurr"), F("flame current"))
|
||||||
@@ -545,6 +551,8 @@ MAKE_PSTR_LIST(tankBottomTemp, F("tankbottomtemp"), F("tank bottom temperature (
|
|||||||
MAKE_PSTR_LIST(tank2BottomTemp, F("tank2bottomtemp"), F("second tank bottom temperature (TS5)"))
|
MAKE_PSTR_LIST(tank2BottomTemp, F("tank2bottomtemp"), F("second tank bottom temperature (TS5)"))
|
||||||
MAKE_PSTR_LIST(heatExchangerTemp, F("heatexchangertemp"), F("heat exchanger temperature (TS6)"))
|
MAKE_PSTR_LIST(heatExchangerTemp, F("heatexchangertemp"), F("heat exchanger temperature (TS6)"))
|
||||||
|
|
||||||
|
MAKE_PSTR_LIST(collectorMaxTemp, F("collectormaxtemp"), F("maximum collector temperature"))
|
||||||
|
MAKE_PSTR_LIST(collectorMinTemp, F("collectormintemp"), F("minimum collector temperature"))
|
||||||
MAKE_PSTR_LIST(tankMaxTemp, F("tankmaxtemp"), F("maximum tank temperature"))
|
MAKE_PSTR_LIST(tankMaxTemp, F("tankmaxtemp"), F("maximum tank temperature"))
|
||||||
MAKE_PSTR_LIST(solarPumpModulation, F("solarpumpmodulation"), F("pump modulation (PS1)"))
|
MAKE_PSTR_LIST(solarPumpModulation, F("solarpumpmodulation"), F("pump modulation (PS1)"))
|
||||||
MAKE_PSTR_LIST(cylinderPumpModulation, F("cylinderpumpmodulation"), F("cylinder pump modulation (PS5)"))
|
MAKE_PSTR_LIST(cylinderPumpModulation, F("cylinderpumpmodulation"), F("cylinder pump modulation (PS5)"))
|
||||||
@@ -554,7 +562,7 @@ MAKE_PSTR_LIST(valveStatus, F("valvestatus"), F("valve status"))
|
|||||||
MAKE_PSTR_LIST(tankHeated, F("tankheated"), F("tank heated"))
|
MAKE_PSTR_LIST(tankHeated, F("tankheated"), F("tank heated"))
|
||||||
MAKE_PSTR_LIST(collectorShutdown, F("collectorshutdown"), F("collector shutdown"))
|
MAKE_PSTR_LIST(collectorShutdown, F("collectorshutdown"), F("collector shutdown"))
|
||||||
|
|
||||||
MAKE_PSTR_LIST(pumpWorkTime, F("pumpWorktime"), F("pump working time"))
|
MAKE_PSTR_LIST(pumpWorkTime, F("pumpworktime"), F("pump working time"))
|
||||||
|
|
||||||
MAKE_PSTR_LIST(energyLastHour, F("energylasthour"), F("energy last hour"))
|
MAKE_PSTR_LIST(energyLastHour, F("energylasthour"), F("energy last hour"))
|
||||||
MAKE_PSTR_LIST(energyTotal, F("energytotal"), F("energy total"))
|
MAKE_PSTR_LIST(energyTotal, F("energytotal"), F("energy total"))
|
||||||
@@ -567,6 +575,13 @@ MAKE_PSTR_LIST(wwTemp5, F("wwtemp5"), F("temperature 5"))
|
|||||||
MAKE_PSTR_LIST(wwTemp7, F("wwtemp7"), F("temperature 7"))
|
MAKE_PSTR_LIST(wwTemp7, F("wwtemp7"), F("temperature 7"))
|
||||||
MAKE_PSTR_LIST(wwPump, F("wwpump"), F("pump"))
|
MAKE_PSTR_LIST(wwPump, F("wwpump"), F("pump"))
|
||||||
|
|
||||||
|
MAKE_PSTR_LIST(wwMinTemp, F("wwmintemp"), F("minimum temperature"))
|
||||||
|
MAKE_PSTR_LIST(pumpMinMod, F("pumpminmod"), F("minimum pump modulation"))
|
||||||
|
MAKE_PSTR_LIST(maxFlow, F("maxflow"), F("maximum solar flow"))
|
||||||
|
MAKE_PSTR_LIST(solarPower, F("solarpower"), F("actual solar power"))
|
||||||
|
MAKE_PSTR_LIST(solarPumpTurnonDiff, F("turnondiff"), F("pump turn on difference"))
|
||||||
|
MAKE_PSTR_LIST(solarPumpTurnoffDiff, F("turnoffdiff"), F("pump turn off difference"))
|
||||||
|
|
||||||
// switch
|
// switch
|
||||||
MAKE_PSTR_LIST(activated, F("activated"), F("activated"))
|
MAKE_PSTR_LIST(activated, F("activated"), F("activated"))
|
||||||
MAKE_PSTR_LIST(status, F("status"), F("status"))
|
MAKE_PSTR_LIST(status, F("status"), F("status"))
|
||||||
|
|||||||
Reference in New Issue
Block a user