mirror of
https://github.com/emsesp/EMS-ESP32.git
synced 2025-12-09 01:09:51 +03:00
move dhw entities from mixer/solar to new water device, add pool device
This commit is contained in:
@@ -176,31 +176,76 @@ Boiler::Boiler(uint8_t device_type, int8_t device_id, uint8_t product_id, const
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(boilTemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&exhaustTemp_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(exhaustTemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&heatblock_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(heatblock),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&headertemp_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(headertemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &burnGas_, DeviceValueType::BOOL, FL_(burnGas), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &burnGas2_, DeviceValueType::BOOL, FL_(burnGas2), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &flameCurr_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flameCurr), DeviceValueUOM::UA);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &heatingPump_, DeviceValueType::BOOL, FL_(heatingPump), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &fanWork_, DeviceValueType::BOOL, FL_(fanWork), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &ignWork_, DeviceValueType::BOOL, FL_(ignWork), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &oilPreHeat_, DeviceValueType::BOOL, FL_(oilPreHeat), DeviceValueUOM::NONE);
|
||||
|
||||
if (model() != EMS_DEVICE_FLAG_HEATPUMP && model() != EMS_DEVICE_FLAG_HIU) {
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&exhaustTemp_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(exhaustTemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&heatblock_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(heatblock),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &burnGas_, DeviceValueType::BOOL, FL_(burnGas), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &burnGas2_, DeviceValueType::BOOL, FL_(burnGas2), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&flameCurr_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(flameCurr),
|
||||
DeviceValueUOM::UA);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &heatingPump_, DeviceValueType::BOOL, FL_(heatingPump), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &fanWork_, DeviceValueType::BOOL, FL_(fanWork), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &ignWork_, DeviceValueType::BOOL, FL_(ignWork), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &oilPreHeat_, DeviceValueType::BOOL, FL_(oilPreHeat), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&burnMinPower_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(burnMinPower),
|
||||
DeviceValueUOM::PERCENT,
|
||||
MAKE_CF_CB(set_min_power));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&burnMaxPower_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(burnMaxPower),
|
||||
DeviceValueUOM::PERCENT,
|
||||
MAKE_CF_CB(set_max_power),
|
||||
0,
|
||||
254);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boilHystOn_, DeviceValueType::INT, FL_(boilHystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst_on), -20, 0);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boilHystOff_, DeviceValueType::INT, FL_(boilHystOff), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst_off), 0, 20);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boil2HystOn_, DeviceValueType::INT, FL_(boil2HystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst2_on), -20, 0);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&boil2HystOff_,
|
||||
DeviceValueType::INT,
|
||||
FL_(boil2HystOff),
|
||||
DeviceValueUOM::DEGREES_R,
|
||||
MAKE_CF_CB(set_hyst2_off),
|
||||
0,
|
||||
20);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&burnMinPeriod_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(burnMinPeriod),
|
||||
DeviceValueUOM::MINUTES,
|
||||
MAKE_CF_CB(set_burn_period),
|
||||
0,
|
||||
120);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &absBurnPow_, DeviceValueType::UINT, FL_(absBurnPow), DeviceValueUOM::PERCENT);
|
||||
}
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&heatingActivated_,
|
||||
DeviceValueType::BOOL,
|
||||
@@ -215,33 +260,8 @@ Boiler::Boiler(uint8_t device_type, int8_t device_id, uint8_t product_id, const
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &pumpMode_, DeviceValueType::ENUM, FL_(enum_pumpMode), FL_(pumpMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_pumpMode));
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &pumpDelay_, DeviceValueType::UINT, FL_(pumpDelay), DeviceValueUOM::MINUTES, MAKE_CF_CB(set_pump_delay), 0, 60);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&burnMinPeriod_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(burnMinPeriod),
|
||||
DeviceValueUOM::MINUTES,
|
||||
MAKE_CF_CB(set_burn_period),
|
||||
0,
|
||||
120);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&burnMinPower_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(burnMinPower),
|
||||
DeviceValueUOM::PERCENT,
|
||||
MAKE_CF_CB(set_min_power));
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &burnMaxPower_, DeviceValueType::UINT, FL_(burnMaxPower), DeviceValueUOM::PERCENT, MAKE_CF_CB(set_max_power), 0, 254);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boilHystOn_, DeviceValueType::INT, FL_(boilHystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst_on), -20, 0);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boilHystOff_, DeviceValueType::INT, FL_(boilHystOff), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst_off), 0, 20);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boil2HystOn_, DeviceValueType::INT, FL_(boil2HystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst2_on), -20, 0);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &boil2HystOff_, DeviceValueType::INT, FL_(boil2HystOff), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_hyst2_off), 0, 20);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &setFlowTemp_, DeviceValueType::UINT, FL_(setFlowTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &setBurnPow_, DeviceValueType::UINT, FL_(setBurnPow), DeviceValueUOM::PERCENT);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &absBurnPow_, DeviceValueType::UINT, FL_(absBurnPow), DeviceValueUOM::PERCENT);
|
||||
register_device_value(
|
||||
DeviceValueTAG::TAG_DEVICE_DATA, &selBurnPow_, DeviceValueType::UINT, FL_(selBurnPow), DeviceValueUOM::PERCENT, MAKE_CF_CB(set_burn_power), 0, 254);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &curBurnPow_, DeviceValueType::UINT, FL_(curBurnPow), DeviceValueUOM::PERCENT);
|
||||
@@ -924,7 +944,7 @@ Boiler::Boiler(uint8_t device_type, int8_t device_id, uint8_t product_id, const
|
||||
EMSESP::send_read_request(0xC2, device_id); // read last errorcode on start (only published on errors)
|
||||
|
||||
|
||||
if (model() != EMS_DEVICE_FLAG_HEATPUMP) {
|
||||
if (model() != EMS_DEVICE_FLAG_HEATPUMP && model() != EMS_DEVICE_FLAG_HIU) {
|
||||
register_telegram_type(0x04, "UBAFactory", true, MAKE_PF_CB(process_UBAFactory));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &nomPower_, DeviceValueType::UINT, FL_(nomPower), DeviceValueUOM::KW, MAKE_CF_CB(set_nomPower));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
@@ -1269,7 +1289,7 @@ void Boiler::process_UBAMonitorFastPlus(std::shared_ptr<const Telegram> telegram
|
||||
has_update(telegram, heatblock_, 23); // see #1317
|
||||
has_update(telegram, headertemp_, 25); // see #1317
|
||||
//has_update(telegram, temperatur_, 27); // unknown temperature
|
||||
telegram->read_value(exhaustTemp1_ , 31);
|
||||
telegram->read_value(exhaustTemp1_, 31);
|
||||
if (Helpers::hasValue(exhaustTemp1_)) {
|
||||
has_update(exhaustTemp_, exhaustTemp1_);
|
||||
}
|
||||
|
||||
@@ -26,61 +26,16 @@ uuid::log::Logger Mixer::logger_{F_(mixer), uuid::log::Facility::CONSOLE};
|
||||
|
||||
Mixer::Mixer(uint8_t device_type, uint8_t device_id, uint8_t product_id, const char * version, const char * name, uint8_t flags, uint8_t brand)
|
||||
: EMSdevice(device_type, device_id, product_id, version, name, flags, brand) {
|
||||
// Pool module
|
||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_MP) {
|
||||
register_telegram_type(0x5BA, "HpPoolStatus", true, MAKE_PF_CB(process_HpPoolStatus));
|
||||
type_ = Type::MP;
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&poolTemp_,
|
||||
DeviceValueType::SHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(poolTemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &poolShuntStatus_, DeviceValueType::ENUM, FL_(enum_shunt), FL_(poolShuntStatus), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &poolShunt_, DeviceValueType::UINT, FL_(poolShunt), DeviceValueUOM::PERCENT);
|
||||
}
|
||||
|
||||
// EMS+
|
||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
if (device_id >= 0x20 && device_id <= 0x27) {
|
||||
register_telegram_type(device_id - 0x20 + 0x02D7, "MMPLUSStatusMessage_HC", false, MAKE_PF_CB(process_MMPLUSStatusMessage_HC));
|
||||
// register_telegram_type(device_id - 0x20 + 0x02E1, "MMPLUSSetMessage_HC", true, MAKE_PF_CB(process_MMPLUSSetMessage_HC));
|
||||
type_ = Type::HC;
|
||||
hc_ = device_id - 0x20 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_HC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempHc), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &status_, DeviceValueType::INT, FL_(mixerStatus), DeviceValueUOM::PERCENT);
|
||||
register_device_value(tag, &flowSetTemp_, DeviceValueType::UINT, FL_(flowSetTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_flowSetTemp));
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(pumpStatus), DeviceValueUOM::NONE, MAKE_CF_CB(set_pump));
|
||||
} else if (device_id >= 0x28 && device_id <= 0x29) {
|
||||
register_telegram_type(device_id - 0x28 + 0x0331, "MMPLUSStatusMessage_WWC", false, MAKE_PF_CB(process_MMPLUSStatusMessage_WWC));
|
||||
register_telegram_type(device_id - 0x28 + 0x0313, "MMPLUSConfigMessage_WWC", true, MAKE_PF_CB(process_MMPLUSConfigMessage_WWC));
|
||||
// register_telegram_type(device_id - 0x28 + 0x033B, "MMPLUSSetMessage_WWC", true, MAKE_PF_CB(process_MMPLUSSetMessage_WWC));
|
||||
type_ = Type::WWC;
|
||||
hc_ = device_id - 0x28 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_WWC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(wwPumpStatus), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &status_, DeviceValueType::INT, FL_(wwTempStatus), DeviceValueUOM::NONE);
|
||||
|
||||
register_device_value(tag, &wwMaxTemp_, DeviceValueType::UINT, FL_(wwMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwMaxTemp));
|
||||
register_device_value(tag, &wwDiffTemp_, DeviceValueType::INT, FL_(wwDiffTemp), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwDiffTemp));
|
||||
register_device_value(tag,
|
||||
&wwDisinfectionTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwDisinfectionTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(tag, &wwReducedTemp_, DeviceValueType::UINT, FL_(wwRedTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwReducedTemp));
|
||||
register_device_value(tag, &wwRequiredTemp_, DeviceValueType::UINT, FL_(wwRequiredTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwRequiredTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwCircPump_,
|
||||
DeviceValueType::BOOL,
|
||||
FL_(wwCircPump),
|
||||
DeviceValueUOM::NONE,
|
||||
MAKE_CF_CB(set_wwCircPump));
|
||||
register_device_value(tag, &wwCircMode_, DeviceValueType::ENUM, FL_(enum_wwCircMode), FL_(wwCircMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCircMode));
|
||||
}
|
||||
register_telegram_type(device_id - 0x20 + 0x02D7, "MMPLUSStatusMessage_HC", false, MAKE_PF_CB(process_MMPLUSStatusMessage_HC));
|
||||
// register_telegram_type(device_id - 0x20 + 0x02E1, "MMPLUSSetMessage_HC", true, MAKE_PF_CB(process_MMPLUSSetMessage_HC));
|
||||
hc_ = device_id - 0x20 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_HC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempHc), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &status_, DeviceValueType::UINT, FL_(mixerStatus), DeviceValueUOM::PERCENT);
|
||||
register_device_value(tag, &flowSetTemp_, DeviceValueType::UINT, FL_(flowSetTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_flowSetTemp));
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(pumpStatus), DeviceValueUOM::NONE, MAKE_CF_CB(set_pump));
|
||||
}
|
||||
|
||||
// EMS 1.0
|
||||
@@ -88,7 +43,6 @@ Mixer::Mixer(uint8_t device_type, uint8_t device_id, uint8_t product_id, const c
|
||||
register_telegram_type(0x00AA, "MMConfigMessage", true, MAKE_PF_CB(process_MMConfigMessage));
|
||||
register_telegram_type(0x00AB, "MMStatusMessage", false, MAKE_PF_CB(process_MMStatusMessage));
|
||||
register_telegram_type(0x00AC, "MMSetMessage", false, MAKE_PF_CB(process_MMSetMessage));
|
||||
type_ = Type::HC;
|
||||
hc_ = device_id - 0x20 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_HC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempHc), DeviceValueUOM::DEGREES);
|
||||
@@ -109,48 +63,16 @@ Mixer::Mixer(uint8_t device_type, uint8_t device_id, uint8_t product_id, const c
|
||||
|
||||
// HT3
|
||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
if (device_id >= 0x40) { // special DHW pos 10
|
||||
register_telegram_type(0x34, "UBAMonitorWW", false, MAKE_PF_CB(process_IPMMonitorWW));
|
||||
register_telegram_type(0x1E, "HydrTemp", false, MAKE_PF_CB(process_IPMHydrTemp));
|
||||
register_telegram_type(0x33, "UBAParameterWW", true, MAKE_PF_CB(process_IPMParameterWW));
|
||||
// register_telegram_type(0x10D, "wwNTCStatus", false, MAKE_PF_CB(process_wwNTCStatus));
|
||||
type_ = Type::WWC;
|
||||
hc_ = device_id - 0x40 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_WWC9 + hc_ - 1;
|
||||
register_device_value(tag, &wwSelTemp_, DeviceValueType::UINT, FL_(wwSelTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwSelTemp));
|
||||
register_device_value(tag, &wwCurTemp_1_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwCurTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwCurTemp_2_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwCurTemp2), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &HydrTemp_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(hydrTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(pumpStatus), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwFlowTempOffset_, DeviceValueType::UINT, FL_(wwFlowTempOffset), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwFlowTempOffset));
|
||||
register_device_value(tag, &wwHystOn_, DeviceValueType::INT, FL_(wwHystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwHystOn));
|
||||
register_device_value(tag, &wwHystOff_, DeviceValueType::INT, FL_(wwHystOff), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwHystOff));
|
||||
register_device_value(tag,
|
||||
&wwDisinfectionTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwDisinfectionTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwCircPump_,
|
||||
DeviceValueType::BOOL,
|
||||
FL_(wwCircPump),
|
||||
DeviceValueUOM::NONE,
|
||||
MAKE_CF_CB(set_wwCircPump));
|
||||
register_device_value(tag, &wwCircMode_, DeviceValueType::ENUM, FL_(enum_wwCircMode), FL_(wwCircMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCircMode));
|
||||
} else {
|
||||
register_telegram_type(0x010C, "IPMStatusMessage", false, MAKE_PF_CB(process_IPMStatusMessage));
|
||||
register_telegram_type(0x011E, "IPMTempMessage", false, MAKE_PF_CB(process_IPMTempMessage));
|
||||
// register_telegram_type(0x0123, "IPMSetMessage", false, MAKE_PF_CB(process_IPMSetMessage));
|
||||
type_ = Type::HC;
|
||||
hc_ = device_id - 0x20 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_HC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempHc), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &status_, DeviceValueType::INT, FL_(mixerStatus), DeviceValueUOM::PERCENT);
|
||||
register_device_value(tag, &flowSetTemp_, DeviceValueType::UINT, FL_(flowSetTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_flowSetTemp));
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(pumpStatus), DeviceValueUOM::NONE, MAKE_CF_CB(set_pump));
|
||||
register_device_value(tag, &flowTempVf_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempVf), DeviceValueUOM::DEGREES);
|
||||
}
|
||||
register_telegram_type(0x010C, "IPMStatusMessage", false, MAKE_PF_CB(process_IPMStatusMessage));
|
||||
register_telegram_type(0x011E, "IPMTempMessage", false, MAKE_PF_CB(process_IPMTempMessage));
|
||||
// register_telegram_type(0x0123, "IPMSetMessage", false, MAKE_PF_CB(process_IPMSetMessage));
|
||||
hc_ = device_id - 0x20 + 1;
|
||||
uint8_t tag = DeviceValueTAG::TAG_HC1 + hc_ - 1;
|
||||
register_device_value(tag, &flowTempHc_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempHc), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &status_, DeviceValueType::UINT, FL_(mixerStatus), DeviceValueUOM::PERCENT);
|
||||
register_device_value(tag, &flowSetTemp_, DeviceValueType::UINT, FL_(flowSetTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_flowSetTemp));
|
||||
register_device_value(tag, &pumpStatus_, DeviceValueType::BOOL, FL_(pumpStatus), DeviceValueUOM::NONE, MAKE_CF_CB(set_pump));
|
||||
register_device_value(tag, &flowTempVf_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(flowTempVf), DeviceValueUOM::DEGREES);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -164,15 +86,6 @@ void Mixer::process_MMPLUSStatusMessage_HC(std::shared_ptr<const Telegram> teleg
|
||||
has_update(telegram, status_, 2); // valve status
|
||||
}
|
||||
|
||||
// Mixer warm water loading/DHW - 0x0331, 0x0332
|
||||
// e.g. A9 00 FF 00 02 32 02 6C 00 3C 00 3C 3C 46 02 03 03 00 3C // on 0x28
|
||||
// A8 00 FF 00 02 31 02 35 00 3C 00 3C 3C 46 02 03 03 00 3C // in 0x29
|
||||
void Mixer::process_MMPLUSStatusMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, flowTempHc_, 0); // is * 10
|
||||
has_bitupdate(telegram, pumpStatus_, 2, 0);
|
||||
has_update(telegram, status_, 11); // temp status
|
||||
}
|
||||
|
||||
// Mixer IPM - 0x010C
|
||||
// e.g. A0 00 FF 00 00 0C 01 00 00 00 00 00 54
|
||||
// A1 00 FF 00 00 0C 02 04 00 01 1D 00 82
|
||||
@@ -200,15 +113,6 @@ void Mixer::process_IPMTempMessage(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, flowTempVf_, 0); // TC1, is * 10
|
||||
}
|
||||
|
||||
// Mixer MP100 for pools - 0x5BA
|
||||
void Mixer::process_HpPoolStatus(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, poolTemp_, 0);
|
||||
has_update(telegram, poolShunt_, 3); // 0-100% how much is the shunt open?
|
||||
telegram->read_value(poolShuntStatus__, 2);
|
||||
uint8_t pss = poolShunt_ == 100 ? 3 : (poolShunt_ == 0 ? 4 : poolShuntStatus__);
|
||||
has_update(poolShuntStatus_, pss);
|
||||
}
|
||||
|
||||
// Mixer on a MM10 - 0xAB
|
||||
// e.g. Mixer Module -> All, type 0xAB, telegram: 21 00 AB 00 2D 01 BE 64 04 01 00 (CRC=15) #data=7
|
||||
// see also https://github.com/emsesp/EMS-ESP/issues/386
|
||||
@@ -235,43 +139,6 @@ void Mixer::process_MMConfigMessage(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, setValveTime_, 1); // valve runtime in 10 sec, max 120 s
|
||||
}
|
||||
|
||||
// Config message 0x313, has to be fetched
|
||||
void Mixer::process_MMPLUSConfigMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwRequiredTemp_, 4);
|
||||
has_update(telegram, wwReducedTemp_, 5);
|
||||
has_update(telegram, wwDiffTemp_, 7);
|
||||
has_update(telegram, wwDisinfectionTemp_, 9);
|
||||
has_update(telegram, wwMaxTemp_, 10);
|
||||
}
|
||||
|
||||
// 0x34 only 8 bytes long
|
||||
// Mixer(0x41) -> All(0x00), UBAMonitorWW(0x34), data: 37 02 1E 02 1E 00 00 00 00
|
||||
void Mixer::process_IPMMonitorWW(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwSelTemp_, 0);
|
||||
has_update(telegram, wwCurTemp_1_, 1);
|
||||
has_update(telegram, wwCurTemp_2_, 3);
|
||||
has_bitupdate(telegram, pumpStatus_, 5, 3);
|
||||
}
|
||||
|
||||
// Mixer(0x41) -> Me(0x0B), UBAParameterWW(0x33), data: 08 FF 46 FB FF 28 FF 07 46 00 FF 00
|
||||
void Mixer::process_IPMParameterWW(std::shared_ptr<const Telegram> telegram) {
|
||||
// has_update(telegram, wwActivated_, 1); // 0xFF means on
|
||||
// has_update(telegram, wwSelTemp_, 2);
|
||||
has_update(telegram, wwHystOn_, 3); // Hyst on (default -5)
|
||||
has_update(telegram, wwHystOff_, 4); // Hyst off (default -1)
|
||||
has_update(telegram, wwFlowTempOffset_, 5); // default 40
|
||||
has_update(telegram, wwCircPump_, 6); // 0xFF means on
|
||||
has_update(telegram, wwCircMode_, 7); // 1=1x3min 6=6x3min 7=continuous
|
||||
has_update(telegram, wwDisinfectionTemp_, 8);
|
||||
// has_bitupdate(telegram, wwChargeType_, 10, 0); // 0 = charge pump, 0xff = 3-way valve
|
||||
}
|
||||
|
||||
|
||||
// 0x1E, only16 bit temperature
|
||||
// Mixer(0x41) -> Boiler(0x08), HydrTemp(0x1E), data: 01 D8
|
||||
void Mixer::process_IPMHydrTemp(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, HydrTemp_, 0);
|
||||
}
|
||||
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wunused-parameter"
|
||||
@@ -284,16 +151,6 @@ void Mixer::process_MMPLUSSetMessage_HC(std::shared_ptr<const Telegram> telegram
|
||||
// pos2: pump
|
||||
}
|
||||
|
||||
// unknown, 2 examples from older threads
|
||||
// Thermostat(0x10) -> Mixer(0x28), ?(0x33B), data: 01 01 00
|
||||
// Thermostat -> Mixing Module, type 0x023B, telegram: 90 28 FF 00 02 3B 00 02 00 (CRC=68)
|
||||
void Mixer::process_MMPLUSSetMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
}
|
||||
|
||||
// MMPLUS telegram 0x345 unknown
|
||||
// Solar Module -> Mixing Module, type 0x0245, telegram: B0 28 FF 00 02 45 64 01 01 (CRC=36)
|
||||
// ?
|
||||
|
||||
// Mixer on a MM10 - 0xAC
|
||||
// e.g. Thermostat -> Mixer Module, type 0xAC, telegram: 10 21 AC 00 1E 64 01 AB
|
||||
void Mixer::process_MMSetMessage(std::shared_ptr<const Telegram> telegram) {
|
||||
@@ -311,15 +168,6 @@ void Mixer::process_IPMSetMessage(std::shared_ptr<const Telegram> telegram) {
|
||||
|
||||
#pragma GCC diagnostic pop
|
||||
|
||||
bool Mixer::set_wwSelTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x35, 3, (uint8_t)temperature, 0x34);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_flowSetTemp(const char * value, const int8_t id) {
|
||||
int v;
|
||||
if (!Helpers::value2number(value, v)) {
|
||||
@@ -389,113 +237,4 @@ bool Mixer::set_setValveTime(const char * value, const int8_t id) {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwMaxTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x313 + wwc, 10, (uint8_t)v, 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwDiffTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x313 + wwc, 7, (int8_t)(v * 10), 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwReducedTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x313 + wwc, 5, (uint8_t)v, 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwRequiredTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x313 + wwc, 4, (uint8_t)v, 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwDisinfectionTemp(const char * value, const int8_t id) {
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 8, (uint8_t)v, 0x33);
|
||||
} else {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
write_command(0x313 + wwc, 9, (uint8_t)v, 0x313 + wwc);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwCircPump(const char * value, const int8_t id) {
|
||||
bool v;
|
||||
if (!Helpers::value2bool(value, v)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 6, v ? 0xFF : 0x00, 0x33);
|
||||
} else {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
write_command(0x33B + wwc, 0, v ? 0x01 : 0x00, 0x33B + wwc);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwCircMode(const char * value, const int8_t id) {
|
||||
uint8_t n;
|
||||
if (!Helpers::value2enum(value, n, FL_(enum_wwCircMode))) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 7, n, 0x33);
|
||||
} else {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
write_command(0x313 + wwc, 0, n, 0x313 + wwc);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwFlowTempOffset(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 5, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwHystOn(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 3, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Mixer::set_wwHystOff(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 4, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
@@ -32,46 +32,18 @@ class Mixer : public EMSdevice {
|
||||
|
||||
void process_MMPLUSStatusMessage_HC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSSetMessage_HC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSStatusMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSSetMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSConfigMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMStatusMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMTempMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMSetMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMStatusMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMConfigMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMSetMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_HpPoolStatus(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
void process_IPMMonitorWW(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMHydrTemp(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMParameterWW(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
bool set_flowSetTemp(const char * value, const int8_t id);
|
||||
bool set_pump(const char * value, const int8_t id);
|
||||
bool set_activated(const char * value, const int8_t id);
|
||||
bool set_setValveTime(const char * value, const int8_t id);
|
||||
|
||||
bool set_wwMaxTemp(const char * value, const int8_t id);
|
||||
bool set_wwDiffTemp(const char * value, const int8_t id);
|
||||
bool set_wwReducedTemp(const char * value, const int8_t id);
|
||||
bool set_wwRequiredTemp(const char * value, const int8_t id);
|
||||
bool set_wwDisinfectionTemp(const char * value, const int8_t id);
|
||||
bool set_wwCircPump(const char * value, const int8_t id);
|
||||
bool set_wwCircMode(const char * value, const int8_t id);
|
||||
|
||||
bool set_wwSelTemp(const char * value, const int8_t id);
|
||||
bool set_wwFlowTempOffset(const char * value, const int8_t id);
|
||||
bool set_wwHystOn(const char * value, const int8_t id);
|
||||
bool set_wwHystOff(const char * value, const int8_t id);
|
||||
|
||||
enum class Type {
|
||||
NONE,
|
||||
HC, // heating circuit
|
||||
WWC, // warm water circuit
|
||||
MP // pool
|
||||
};
|
||||
|
||||
private:
|
||||
uint16_t flowTempHc_;
|
||||
uint16_t flowTempVf_;
|
||||
@@ -81,31 +53,7 @@ class Mixer : public EMSdevice {
|
||||
uint8_t activated_;
|
||||
uint8_t setValveTime_;
|
||||
|
||||
// MM100wwParam - 0x0313, 0x033B
|
||||
uint8_t wwMaxTemp_;
|
||||
uint8_t wwRequiredTemp_;
|
||||
uint8_t wwReducedTemp_;
|
||||
uint8_t wwDiffTemp_;
|
||||
uint8_t wwDisinfectionTemp_;
|
||||
uint8_t wwCircPump_;
|
||||
uint8_t wwCircMode_;
|
||||
|
||||
// MP100 pool
|
||||
int16_t poolTemp_;
|
||||
uint8_t poolShuntStatus_;
|
||||
uint8_t poolShunt_;
|
||||
|
||||
Type type_ = Type::NONE;
|
||||
uint16_t hc_ = EMS_VALUE_USHORT_NOTSET;
|
||||
uint8_t poolShuntStatus__ = EMS_VALUE_UINT_NOTSET; // temp value
|
||||
|
||||
uint8_t wwSelTemp_;
|
||||
uint16_t wwCurTemp_1_;
|
||||
uint16_t wwCurTemp_2_;
|
||||
uint16_t HydrTemp_;
|
||||
int8_t wwHystOn_; // Hyst on (default -5)
|
||||
int8_t wwHystOff_; // Hyst off (default -1)
|
||||
uint8_t wwFlowTempOffset_; // default 40
|
||||
};
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
50
src/devices/pool.cpp
Normal file
50
src/devices/pool.cpp
Normal file
@@ -0,0 +1,50 @@
|
||||
/*
|
||||
* EMS-ESP - https://github.com/emsesp/EMS-ESP
|
||||
* Copyright 2020-2023 Paul Derbyshire
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "pool.h"
|
||||
|
||||
namespace emsesp {
|
||||
|
||||
REGISTER_FACTORY(Pool, EMSdevice::DeviceType::POOL);
|
||||
|
||||
uuid::log::Logger Pool::logger_{F_(pool), uuid::log::Facility::CONSOLE};
|
||||
|
||||
Pool::Pool(uint8_t device_type, uint8_t device_id, uint8_t product_id, const char * version, const char * name, uint8_t flags, uint8_t brand)
|
||||
: EMSdevice(device_type, device_id, product_id, version, name, flags, brand) {
|
||||
// Pool module
|
||||
register_telegram_type(0x5BA, "HpPoolStatus", true, MAKE_PF_CB(process_HpPoolStatus));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&poolTemp_,
|
||||
DeviceValueType::SHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(poolTemp),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &poolShuntStatus_, DeviceValueType::ENUM, FL_(enum_shunt), FL_(poolShuntStatus), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA, &poolShunt_, DeviceValueType::UINT, FL_(poolShunt), DeviceValueUOM::PERCENT);
|
||||
}
|
||||
|
||||
// Mixer MP100 for pools - 0x5BA
|
||||
void Pool::process_HpPoolStatus(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, poolTemp_, 0);
|
||||
has_update(telegram, poolShunt_, 3); // 0-100% how much is the shunt open?
|
||||
telegram->read_value(poolShuntStatus__, 2);
|
||||
uint8_t pss = poolShunt_ == 100 ? 3 : (poolShunt_ == 0 ? 4 : poolShuntStatus__);
|
||||
has_update(poolShuntStatus_, pss);
|
||||
}
|
||||
|
||||
} // namespace emsesp
|
||||
46
src/devices/pool.h
Normal file
46
src/devices/pool.h
Normal file
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* EMS-ESP - https://github.com/emsesp/EMS-ESP
|
||||
* Copyright 2020-2023 Paul Derbyshire
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef EMSESP_POOL_H
|
||||
#define EMSESP_POOL_H
|
||||
|
||||
#include "emsesp.h"
|
||||
|
||||
namespace emsesp {
|
||||
|
||||
class Pool : public EMSdevice {
|
||||
public:
|
||||
Pool(uint8_t device_type, uint8_t device_id, uint8_t product_id, const char * version, const char * name, uint8_t flags, uint8_t brand);
|
||||
|
||||
private:
|
||||
static uuid::log::Logger logger_;
|
||||
|
||||
void process_HpPoolStatus(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
private:
|
||||
// MP100 pool
|
||||
int16_t poolTemp_;
|
||||
uint8_t poolShuntStatus_;
|
||||
uint8_t poolShunt_;
|
||||
|
||||
uint8_t poolShuntStatus__ = EMS_VALUE_UINT_NOTSET; // temp value
|
||||
};
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
#endif
|
||||
@@ -34,32 +34,22 @@ Solar::Solar(uint8_t device_type, uint8_t device_id, uint8_t product_id, const c
|
||||
}
|
||||
|
||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_SM100) {
|
||||
if (device_id == 0x2A) { // SM100 DHW
|
||||
register_telegram_type(0x07D6, "SM100wwTemperature", false, MAKE_PF_CB(process_SM100wwTemperature));
|
||||
register_telegram_type(0x07AA, "SM100wwStatus", false, MAKE_PF_CB(process_SM100wwStatus));
|
||||
register_telegram_type(0x07AB, "SM100wwCommand", false, MAKE_PF_CB(process_SM100wwCommand));
|
||||
register_telegram_type(0x07A5, "SM100wwCirc", true, MAKE_PF_CB(process_SM100wwCirc));
|
||||
register_telegram_type(0x07A6, "SM100wwParam", true, MAKE_PF_CB(process_SM100wwParam));
|
||||
register_telegram_type(0x07AE, "SM100wwKeepWarm", true, MAKE_PF_CB(process_SM100wwKeepWarm));
|
||||
register_telegram_type(0x07E0, "SM100wwStatus2", true, MAKE_PF_CB(process_SM100wwStatus2));
|
||||
} else {
|
||||
// F9 is not a telegram type, it's a flag for configure
|
||||
// register_telegram_type(0xF9, "ParamCfg", false, MAKE_PF_CB(process_SM100ParamCfg));
|
||||
register_telegram_type(0x0358, "SM100SystemConfig", true, MAKE_PF_CB(process_SM100SystemConfig));
|
||||
register_telegram_type(0x035A, "SM100CircuitConfig", true, MAKE_PF_CB(process_SM100CircuitConfig));
|
||||
register_telegram_type(0x035D, "SM100Circuit2Config", true, MAKE_PF_CB(process_SM100Circuit2Config));
|
||||
register_telegram_type(0x0362, "SM100Monitor", false, MAKE_PF_CB(process_SM100Monitor));
|
||||
register_telegram_type(0x0363, "SM100Monitor2", false, MAKE_PF_CB(process_SM100Monitor2));
|
||||
register_telegram_type(0x0366, "SM100Config", false, MAKE_PF_CB(process_SM100Config));
|
||||
register_telegram_type(0x0364, "SM100Status", false, MAKE_PF_CB(process_SM100Status));
|
||||
register_telegram_type(0x036A, "SM100Status2", false, MAKE_PF_CB(process_SM100Status2));
|
||||
register_telegram_type(0x0380, "SM100CollectorConfig", true, MAKE_PF_CB(process_SM100CollectorConfig));
|
||||
register_telegram_type(0x038E, "SM100Energy", true, MAKE_PF_CB(process_SM100Energy));
|
||||
register_telegram_type(0x0391, "SM100Time", true, MAKE_PF_CB(process_SM100Time));
|
||||
register_telegram_type(0x035F, "SM100Config1", true, MAKE_PF_CB(process_SM100Config1));
|
||||
register_telegram_type(0x035C, "SM100HeatAssist", true, MAKE_PF_CB(process_SM100HeatAssist));
|
||||
register_telegram_type(0x0361, "SM100Differential", true, MAKE_PF_CB(process_SM100Differential));
|
||||
}
|
||||
// F9 is not a telegram type, it's a flag for configure
|
||||
// register_telegram_type(0xF9, "ParamCfg", false, MAKE_PF_CB(process_SM100ParamCfg));
|
||||
register_telegram_type(0x0358, "SM100SystemConfig", true, MAKE_PF_CB(process_SM100SystemConfig));
|
||||
register_telegram_type(0x035A, "SM100CircuitConfig", true, MAKE_PF_CB(process_SM100CircuitConfig));
|
||||
register_telegram_type(0x035D, "SM100Circuit2Config", true, MAKE_PF_CB(process_SM100Circuit2Config));
|
||||
register_telegram_type(0x0362, "SM100Monitor", false, MAKE_PF_CB(process_SM100Monitor));
|
||||
register_telegram_type(0x0363, "SM100Monitor2", false, MAKE_PF_CB(process_SM100Monitor2));
|
||||
register_telegram_type(0x0366, "SM100Config", false, MAKE_PF_CB(process_SM100Config));
|
||||
register_telegram_type(0x0364, "SM100Status", false, MAKE_PF_CB(process_SM100Status));
|
||||
register_telegram_type(0x036A, "SM100Status2", false, MAKE_PF_CB(process_SM100Status2));
|
||||
register_telegram_type(0x0380, "SM100CollectorConfig", true, MAKE_PF_CB(process_SM100CollectorConfig));
|
||||
register_telegram_type(0x038E, "SM100Energy", true, MAKE_PF_CB(process_SM100Energy));
|
||||
register_telegram_type(0x0391, "SM100Time", true, MAKE_PF_CB(process_SM100Time));
|
||||
register_telegram_type(0x035F, "SM100Config1", true, MAKE_PF_CB(process_SM100Config1));
|
||||
register_telegram_type(0x035C, "SM100HeatAssist", true, MAKE_PF_CB(process_SM100HeatAssist));
|
||||
register_telegram_type(0x0361, "SM100Differential", true, MAKE_PF_CB(process_SM100Differential));
|
||||
}
|
||||
|
||||
if (flags == EMSdevice::EMS_DEVICE_FLAG_ISM) {
|
||||
@@ -69,94 +59,6 @@ Solar::Solar(uint8_t device_type, uint8_t device_id, uint8_t product_id, const c
|
||||
}
|
||||
|
||||
// device values...
|
||||
// special case for a SM100 DHW device_id with 0x2A where it's not actual a solar module
|
||||
if (device_id == 0x2A) {
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwTemp_1_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwTemp1),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwTemp_3_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwTemp3),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwTemp_4_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwTemp4),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwTemp_5_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwTemp5),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwTemp_7_,
|
||||
DeviceValueType::USHORT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwTemp7),
|
||||
DeviceValueUOM::DEGREES);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW, &wwPump_, DeviceValueType::BOOL, FL_(wwPump), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwMaxTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwMaxTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwMaxTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwSelTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwSelTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwSelTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwRedTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwRedTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwRedTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwDailyTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwDailyTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwDailyTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwDisinfectionTemp_,
|
||||
DeviceValueType::UINT,
|
||||
FL_(wwDisinfectionTemp),
|
||||
DeviceValueUOM::DEGREES,
|
||||
MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW, &wwCirc_, DeviceValueType::BOOL, FL_(wwCirc), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCirc));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwCircMode_,
|
||||
DeviceValueType::ENUM,
|
||||
FL_(enum_wwCircMode),
|
||||
FL_(wwCircMode),
|
||||
DeviceValueUOM::NONE,
|
||||
MAKE_CF_CB(set_wwCircMode));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwKeepWarm_,
|
||||
DeviceValueType::BOOL,
|
||||
FL_(wwKeepWarm),
|
||||
DeviceValueUOM::NONE,
|
||||
MAKE_CF_CB(set_wwKeepWarm));
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW, &wwStatus2_, DeviceValueType::ENUM, FL_(enum_wwStatus2), FL_(wwStatus2), DeviceValueUOM::NONE);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW, &wwPumpMod_, DeviceValueType::UINT, FL_(wwPumpMod), DeviceValueUOM::PERCENT);
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA_WW,
|
||||
&wwFlow_,
|
||||
DeviceValueType::UINT,
|
||||
DeviceValueNumOp::DV_NUMOP_DIV10,
|
||||
FL_(wwFlow),
|
||||
DeviceValueUOM::LMIN);
|
||||
return;
|
||||
}
|
||||
|
||||
// common solar values for all modules (except dhw)
|
||||
register_device_value(DeviceValueTAG::TAG_DEVICE_DATA,
|
||||
&collectorTemp_,
|
||||
@@ -690,58 +592,6 @@ void Solar::process_SM100Monitor(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, retHeatAssist_, 10); // is *10 - TS15: return temperature heating assistance
|
||||
}
|
||||
|
||||
// SM100wwTemperature - 0x07D6
|
||||
// Solar Module(0x2A) -> (0x00), (0x7D6), data: 01 C1 00 00 02 5B 01 AF 01 AD 80 00 01 90
|
||||
void Solar::process_SM100wwTemperature(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwTemp_1_, 0); // is *10
|
||||
has_update(telegram, wwTemp_3_, 4); // is *10
|
||||
has_update(telegram, wwTemp_4_, 6); // is *10
|
||||
has_update(telegram, wwTemp_5_, 8); // is *10
|
||||
has_update(telegram, wwTemp_7_, 12); // is *10
|
||||
}
|
||||
|
||||
// SM100wwStatus - 0x07AA
|
||||
// Solar Module(0x2A) -> (0x00), (0x7AA), data: 64 00 04 00 03 00 28 01 0F
|
||||
void Solar::process_SM100wwStatus(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwPump_, 0);
|
||||
}
|
||||
|
||||
// SM100wwParam - 0x07A6, Solar Module(0x2A) -> (0x00)
|
||||
// data: FF 05 0F 5F 00 01 3C 3C 3C 3C 28 12 46 01 3C 1E 03 07 3C 00 0F 00 05
|
||||
void Solar::process_SM100wwParam(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwMaxTemp_, 8);
|
||||
has_update(telegram, wwSelTemp_, 9);
|
||||
has_update(telegram, wwRedTemp_, 10);
|
||||
has_update(telegram, wwDailyTemp_, 6);
|
||||
has_update(telegram, wwDisinfectionTemp_, 12);
|
||||
// (daily heating time thermostat 2F5, offset 9, offset 8 on/off)
|
||||
}
|
||||
|
||||
// SM100wwCirc - 0x07A5
|
||||
// Solar Module(0x2A) -> (0x00), (0x7A5), data:
|
||||
void Solar::process_SM100wwCirc(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwCirc_, 0);
|
||||
has_update(telegram, wwCircMode_, 3);
|
||||
}
|
||||
|
||||
// SM100wwKeepWarm - 0x7AE, keepWarm
|
||||
// Thermostat(0x10) -> Solar(0x2A), ?(0x7AE), data: FF
|
||||
void Solar::process_SM100wwKeepWarm(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwKeepWarm_, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
// SM100ww? - 0x7E0, some kind of status
|
||||
// data: 00 00 46 00 00 01 06 0E 06 0E 00 00 00 00 00 03 03 03 03
|
||||
// publishes single values offset 1/2(16bit), offset 5, offset 6, offset 7, offset 8, offset 9,
|
||||
// status2 = 03:"no heat", 06:"heat request", 08:"disinfecting", 09:"hold"
|
||||
*/
|
||||
void Solar::process_SM100wwStatus2(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwFlow_, 7);
|
||||
has_update(telegram, wwStatus2_, 8);
|
||||
has_update(telegram, wwPumpMod_, 9);
|
||||
}
|
||||
|
||||
// SM100Monitor2 - 0x0363 Heatcounter
|
||||
// e.g. B0 00 FF 00 02 63 80 00 80 00 00 00 80 00 80 00 80 00 00 80 00 5A
|
||||
// Solar(0x30) -> All(0x00), SM100Monitor2(0x363), data: 01 E1 01 6B 00 00 01 5D 02 8E 80 00 0F 80 00
|
||||
@@ -753,17 +603,6 @@ void Solar::process_SM100Monitor2(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram->read_value(swapFlowTemp_, 8)); // is *10
|
||||
}
|
||||
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wunused-parameter"
|
||||
|
||||
// SM100wwCommand - 0x07AB
|
||||
// Thermostat(0x10) -> Solar Module(0x2A), (0x7AB), data: 01 00 01
|
||||
void Solar::process_SM100wwCommand(std::shared_ptr<const Telegram> telegram) {
|
||||
// not implemented yet
|
||||
}
|
||||
|
||||
#pragma GCC diagnostic pop
|
||||
|
||||
// SM100Config - 0x0366
|
||||
// e.g. B0 00 FF 00 02 66 01 62 00 13 40 14
|
||||
void Solar::process_SM100Config(std::shared_ptr<const Telegram> telegram) {
|
||||
@@ -1249,76 +1088,4 @@ bool Solar::set_diffControl(const char * value, const int8_t id) {
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwSelTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 9, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwMaxTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 8, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwRedTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 10, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwDailyTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 6, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwDisinfectionTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 12, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwCirc(const char * value, const int8_t id) {
|
||||
bool b;
|
||||
if (!Helpers::value2bool(value, b)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A5, 0, b ? 0xFF : 0x00, 0x7A5);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwCircMode(const char * value, const int8_t id) {
|
||||
uint8_t num;
|
||||
if (!Helpers::value2enum(value, num, FL_(enum_wwCircMode))) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A5, 3, num, 0x7A5);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Solar::set_wwKeepWarm(const char * value, const int8_t id) {
|
||||
bool b;
|
||||
if (!Helpers::value2bool(value, b)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7AE, 0, b ? 0xFF : 0x00, 0x7AE);
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
@@ -114,35 +114,6 @@ class Solar : public EMSdevice {
|
||||
uint16_t collector2Area_; // Area of collector field 2
|
||||
uint8_t collector2Type_; // Type of collector field 2, 01=flat, 02=vacuum
|
||||
|
||||
// SM100wwTemperature - 0x07D6
|
||||
uint16_t wwTemp_1_;
|
||||
uint16_t wwTemp_3_;
|
||||
uint16_t wwTemp_4_;
|
||||
uint16_t wwTemp_5_;
|
||||
uint16_t wwTemp_7_;
|
||||
|
||||
// SM100wwStatus - 0x07AA
|
||||
uint8_t wwPump_;
|
||||
|
||||
// SM100wwParam - 0x07A6
|
||||
uint8_t wwMaxTemp_;
|
||||
uint8_t wwSelTemp_;
|
||||
uint8_t wwRedTemp_;
|
||||
uint8_t wwDailyTemp_;
|
||||
uint8_t wwDisinfectionTemp_;
|
||||
|
||||
// SM100wwKeepWarm - 0x07AE
|
||||
uint8_t wwKeepWarm_;
|
||||
|
||||
// SM100wwCirc - 0x07A5
|
||||
uint8_t wwCirc_;
|
||||
uint8_t wwCircMode_;
|
||||
|
||||
// SM100wwStatus2 - 0x07E0
|
||||
uint8_t wwFlow_;
|
||||
uint8_t wwPumpMod_;
|
||||
uint8_t wwStatus2_;
|
||||
|
||||
// SM10Config - 0x96
|
||||
uint8_t wwMinTemp_;
|
||||
uint8_t maxFlow_; // set this to calculate power
|
||||
@@ -178,14 +149,6 @@ class Solar : public EMSdevice {
|
||||
void process_SM100HeatAssist(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100Differential(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
void process_SM100wwTemperature(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwStatus(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwStatus2(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwCommand(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwCirc(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwParam(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwKeepWarm(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
void process_ISM1StatusMessage(std::shared_ptr<const Telegram> telegram);
|
||||
void process_ISM1Set(std::shared_ptr<const Telegram> telegram);
|
||||
void process_ISM2StatusMessage(std::shared_ptr<const Telegram> telegram);
|
||||
@@ -226,14 +189,6 @@ class Solar : public EMSdevice {
|
||||
bool set_heatAssist(const char * value, const int8_t id);
|
||||
bool set_diffControl(const char * value, const int8_t id);
|
||||
|
||||
bool set_wwSelTemp(const char * value, const int8_t id);
|
||||
bool set_wwMaxTemp(const char * value, const int8_t id);
|
||||
bool set_wwRedTemp(const char * value, const int8_t id);
|
||||
bool set_wwCirc(const char * value, const int8_t id);
|
||||
bool set_wwCircMode(const char * value, const int8_t id);
|
||||
bool set_wwKeepWarm(const char * value, const int8_t id);
|
||||
bool set_wwDisinfectionTemp(const char * value, const int8_t id);
|
||||
bool set_wwDailyTemp(const char * value, const int8_t id);
|
||||
};
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
392
src/devices/water.cpp
Normal file
392
src/devices/water.cpp
Normal file
@@ -0,0 +1,392 @@
|
||||
/*
|
||||
* EMS-ESP - https://github.com/emsesp/EMS-ESP
|
||||
* Copyright 2020-2023 Paul Derbyshire
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "water.h"
|
||||
|
||||
namespace emsesp {
|
||||
|
||||
REGISTER_FACTORY(Water, EMSdevice::DeviceType::WATER);
|
||||
|
||||
uuid::log::Logger Water::logger_{F_(water), uuid::log::Facility::CONSOLE};
|
||||
|
||||
Water::Water(uint8_t device_type, uint8_t device_id, uint8_t product_id, const char * version, const char * name, uint8_t flags, uint8_t brand)
|
||||
: EMSdevice(device_type, device_id, product_id, version, name, flags, brand) {
|
||||
uint8_t tag = DeviceValueTAG::TAG_WWC1 + device_id - EMSdevice::EMS_DEVICE_ID_DHW1;
|
||||
if (device_id == 0x2A) { // SM100, DHW3
|
||||
wwc_ = 2;
|
||||
// telegram handlers
|
||||
register_telegram_type(0x07D6, "SM100wwTemperature", false, MAKE_PF_CB(process_SM100wwTemperature));
|
||||
register_telegram_type(0x07AA, "SM100wwStatus", false, MAKE_PF_CB(process_SM100wwStatus));
|
||||
register_telegram_type(0x07AB, "SM100wwCommand", false, MAKE_PF_CB(process_SM100wwCommand));
|
||||
register_telegram_type(0x07A5, "SM100wwCirc", true, MAKE_PF_CB(process_SM100wwCirc));
|
||||
register_telegram_type(0x07A6, "SM100wwParam", true, MAKE_PF_CB(process_SM100wwParam));
|
||||
register_telegram_type(0x07AE, "SM100wwKeepWarm", true, MAKE_PF_CB(process_SM100wwKeepWarm));
|
||||
register_telegram_type(0x07E0, "SM100wwStatus2", true, MAKE_PF_CB(process_SM100wwStatus2));
|
||||
// device values...
|
||||
register_device_value(tag, &wwTemp_1_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp1), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_2_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp2), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_3_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp3), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_4_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp4), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_5_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp5), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_6_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp6), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_7_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp7), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwPump_, DeviceValueType::BOOL, FL_(wwPump), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwMaxTemp_, DeviceValueType::UINT, FL_(wwMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwMaxTemp));
|
||||
register_device_value(tag, &wwSelTemp_, DeviceValueType::UINT, FL_(wwSelTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwSelTemp));
|
||||
register_device_value(tag, &wwRedTemp_, DeviceValueType::UINT, FL_(wwRedTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwRedTemp));
|
||||
register_device_value(tag, &wwDailyTemp_, DeviceValueType::UINT, FL_(wwDailyTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwDailyTemp));
|
||||
register_device_value(tag, &wwDisinfectionTemp_, DeviceValueType::UINT, FL_(wwDisinfectionTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(tag, &wwCirc_, DeviceValueType::BOOL, FL_(wwCirc), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCirc));
|
||||
register_device_value(tag, &wwCircMode_, DeviceValueType::ENUM, FL_(enum_wwCircMode), FL_(wwCircMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCircMode));
|
||||
register_device_value(tag, &wwKeepWarm_, DeviceValueType::BOOL, FL_(wwKeepWarm), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwKeepWarm));
|
||||
register_device_value(tag, &wwStatus2_, DeviceValueType::ENUM, FL_(enum_wwStatus2), FL_(wwStatus2), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwPumpMod_, DeviceValueType::UINT, FL_(wwPumpMod), DeviceValueUOM::PERCENT);
|
||||
register_device_value(tag, &wwFlow_, DeviceValueType::UINT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwFlow), DeviceValueUOM::LMIN);
|
||||
|
||||
} else if (device_id >= EMSdevice::EMS_DEVICE_ID_DHW1 && device_id <= EMSdevice::EMS_DEVICE_ID_DHW2) {
|
||||
wwc_ = device_id - EMSdevice::EMS_DEVICE_ID_DHW1;
|
||||
register_telegram_type(0x331 + wwc_, "MMPLUSStatusMessage_WWC", false, MAKE_PF_CB(process_MMPLUSStatusMessage_WWC));
|
||||
register_telegram_type(0x313 + wwc_, "MMPLUSConfigMessage_WWC", true, MAKE_PF_CB(process_MMPLUSConfigMessage_WWC));
|
||||
// register_telegram_type(0x33B + type_offset, "MMPLUSSetMessage_WWC", true, MAKE_PF_CB(process_MMPLUSSetMessage_WWC));
|
||||
// device values...
|
||||
register_device_value(tag, &wwFlowTemp_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwStatus_, DeviceValueType::INT, FL_(wwTempStatus), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwPump_, DeviceValueType::BOOL, FL_(wwPump), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwMaxTemp_, DeviceValueType::UINT, FL_(wwMaxTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwMaxTemp));
|
||||
register_device_value(tag, &wwDiffTemp_, DeviceValueType::INT, FL_(wwDiffTemp), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwDiffTemp));
|
||||
register_device_value(tag, &wwDisinfectionTemp_, DeviceValueType::UINT, FL_(wwDisinfectionTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(tag, &wwRedTemp_, DeviceValueType::UINT, FL_(wwRedTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwRedTemp));
|
||||
register_device_value(tag, &wwRequiredTemp_, DeviceValueType::UINT, FL_(wwRequiredTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwRequiredTemp));
|
||||
register_device_value(tag, &wwCirc_, DeviceValueType::BOOL, FL_(wwCirc), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCirc));
|
||||
register_device_value(tag, &wwCircMode_, DeviceValueType::ENUM, FL_(enum_wwCircMode), FL_(wwCircMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCircMode));
|
||||
} else if (device_id == 0x40) { // flags == EMSdevice::EMS_DEVICE_FLAG_IPM, special DHW pos 10
|
||||
wwc_ = 0;
|
||||
tag = DeviceValueTAG::TAG_WWC1;
|
||||
register_telegram_type(0x34, "UBAMonitorWW", false, MAKE_PF_CB(process_IPMMonitorWW));
|
||||
register_telegram_type(0x1E, "HydrTemp", false, MAKE_PF_CB(process_IPMHydrTemp));
|
||||
register_telegram_type(0x33, "UBAParameterWW", true, MAKE_PF_CB(process_IPMParameterWW));
|
||||
// register_telegram_type(0x10D, "wwNTCStatus", false, MAKE_PF_CB(process_wwNTCStatus));
|
||||
// device values...
|
||||
register_device_value(tag, &wwSelTemp_, DeviceValueType::UINT, FL_(wwSelTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwSelTemp));
|
||||
register_device_value(tag, &wwTemp_1_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp1), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwTemp_2_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(wwTemp2), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &HydrTemp_, DeviceValueType::USHORT, DeviceValueNumOp::DV_NUMOP_DIV10, FL_(hydrTemp), DeviceValueUOM::DEGREES);
|
||||
register_device_value(tag, &wwPump_, DeviceValueType::BOOL, FL_(wwPump), DeviceValueUOM::NONE);
|
||||
register_device_value(tag, &wwFlowTempOffset_, DeviceValueType::UINT, FL_(wwFlowTempOffset), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwFlowTempOffset));
|
||||
register_device_value(tag, &wwHystOn_, DeviceValueType::INT, FL_(wwHystOn), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwHystOn));
|
||||
register_device_value(tag, &wwHystOff_, DeviceValueType::INT, FL_(wwHystOff), DeviceValueUOM::DEGREES_R, MAKE_CF_CB(set_wwHystOff));
|
||||
register_device_value(tag, &wwDisinfectionTemp_, DeviceValueType::UINT, FL_(wwDisinfectionTemp), DeviceValueUOM::DEGREES, MAKE_CF_CB(set_wwDisinfectionTemp));
|
||||
register_device_value(tag, &wwCirc_, DeviceValueType::BOOL, FL_(wwCirc), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCirc));
|
||||
register_device_value(tag, &wwCircMode_, DeviceValueType::ENUM, FL_(enum_wwCircMode), FL_(wwCircMode), DeviceValueUOM::NONE, MAKE_CF_CB(set_wwCircMode));
|
||||
}
|
||||
}
|
||||
|
||||
// SM100wwTemperature - 0x07D6
|
||||
// Solar Module(0x2A) -> (0x00), (0x7D6), data: 01 C1 00 00 02 5B 01 AF 01 AD 80 00 01 90
|
||||
void Water::process_SM100wwTemperature(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwTemp_1_, 0); // is *10
|
||||
has_update(telegram, wwTemp_2_, 2); // is *10
|
||||
has_update(telegram, wwTemp_3_, 4); // is *10
|
||||
has_update(telegram, wwTemp_4_, 6); // is *10
|
||||
has_update(telegram, wwTemp_5_, 8); // is *10
|
||||
has_update(telegram, wwTemp_6_, 10); // is *10
|
||||
has_update(telegram, wwTemp_7_, 12); // is *10
|
||||
}
|
||||
|
||||
// SM100wwStatus - 0x07AA
|
||||
// Solar Module(0x2A) -> (0x00), (0x7AA), data: 64 00 04 00 03 00 28 01 0F
|
||||
void Water::process_SM100wwStatus(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwPump_, 0);
|
||||
}
|
||||
|
||||
// SM100wwParam - 0x07A6, Solar Module(0x2A) -> (0x00)
|
||||
// data: FF 05 0F 5F 00 01 3C 3C 3C 3C 28 12 46 01 3C 1E 03 07 3C 00 0F 00 05
|
||||
void Water::process_SM100wwParam(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwMaxTemp_, 8);
|
||||
has_update(telegram, wwSelTemp_, 9);
|
||||
has_update(telegram, wwRedTemp_, 10);
|
||||
has_update(telegram, wwDailyTemp_, 6);
|
||||
has_update(telegram, wwDisinfectionTemp_, 12);
|
||||
// (daily heating time thermostat 2F5, offset 9, offset 8 on/off)
|
||||
}
|
||||
|
||||
// SM100wwCirc - 0x07A5
|
||||
// Solar Module(0x2A) -> (0x00), (0x7A5), data:
|
||||
void Water::process_SM100wwCirc(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwCirc_, 0);
|
||||
has_update(telegram, wwCircMode_, 3);
|
||||
}
|
||||
|
||||
// SM100wwKeepWarm - 0x7AE, keepWarm
|
||||
// Thermostat(0x10) -> Solar(0x2A), ?(0x7AE), data: FF
|
||||
void Water::process_SM100wwKeepWarm(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwKeepWarm_, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
// SM100ww? - 0x7E0, some kind of status
|
||||
// data: 00 00 46 00 00 01 06 0E 06 0E 00 00 00 00 00 03 03 03 03
|
||||
// publishes single values offset 1/2(16bit), offset 5, offset 6, offset 7, offset 8, offset 9,
|
||||
// status2 = 03:"no heat", 06:"heat request", 08:"disinfecting", 09:"hold"
|
||||
*/
|
||||
void Water::process_SM100wwStatus2(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwFlow_, 7);
|
||||
has_update(telegram, wwStatus2_, 8);
|
||||
has_update(telegram, wwPumpMod_, 9);
|
||||
}
|
||||
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wunused-parameter"
|
||||
// SM100wwCommand - 0x07AB
|
||||
// Thermostat(0x10) -> Solar Module(0x2A), (0x7AB), data: 01 00 01
|
||||
void Water::process_SM100wwCommand(std::shared_ptr<const Telegram> telegram) {
|
||||
// not implemented yet
|
||||
}
|
||||
#pragma GCC diagnostic pop
|
||||
|
||||
/*
|
||||
* MM100 messages
|
||||
*/
|
||||
|
||||
// Mixer warm water loading/DHW - 0x0331, 0x0332
|
||||
// e.g. A9 00 FF 00 02 32 02 6C 00 3C 00 3C 3C 46 02 03 03 00 3C // on 0x28
|
||||
// A8 00 FF 00 02 31 02 35 00 3C 00 3C 3C 46 02 03 03 00 3C // in 0x29
|
||||
void Water::process_MMPLUSStatusMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwFlowTemp_, 0); // is * 10
|
||||
has_bitupdate(telegram, wwPump_, 2, 0);
|
||||
has_update(telegram, wwStatus_, 11); // temp status
|
||||
}
|
||||
|
||||
// Config message 0x313, has to be fetched
|
||||
void Water::process_MMPLUSConfigMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwRequiredTemp_, 4);
|
||||
has_update(telegram, wwRedTemp_, 5);
|
||||
has_update(telegram, wwDiffTemp_, 7);
|
||||
has_update(telegram, wwDisinfectionTemp_, 9);
|
||||
has_update(telegram, wwMaxTemp_, 10);
|
||||
}
|
||||
|
||||
// unknown, 2 examples from older threads
|
||||
// Thermostat(0x10) -> Mixer(0x28), ?(0x33B), data: 01 01 00
|
||||
// Thermostat -> Mixing Module, type 0x023B, telegram: 90 28 FF 00 02 3B 00 02 00 (CRC=68)
|
||||
void Water::process_MMPLUSSetMessage_WWC(std::shared_ptr<const Telegram> telegram) {
|
||||
}
|
||||
|
||||
// MMPLUS telegram 0x345 unknown
|
||||
// Solar Module -> Mixing Module, type 0x0245, telegram: B0 28 FF 00 02 45 64 01 01 (CRC=36)
|
||||
// ?
|
||||
|
||||
/*
|
||||
* IPM messages
|
||||
*/
|
||||
|
||||
// 0x34 only 8 bytes long
|
||||
// Mixer(0x41) -> All(0x00), UBAMonitorWW(0x34), data: 37 02 1E 02 1E 00 00 00 00
|
||||
void Water::process_IPMMonitorWW(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, wwSelTemp_, 0);
|
||||
has_update(telegram, wwTemp_1_, 1);
|
||||
has_update(telegram, wwTemp_2_, 3);
|
||||
has_bitupdate(telegram, wwPump_, 5, 3);
|
||||
}
|
||||
|
||||
// Mixer(0x41) -> Me(0x0B), UBAParameterWW(0x33), data: 08 FF 46 FB FF 28 FF 07 46 00 FF 00
|
||||
void Water::process_IPMParameterWW(std::shared_ptr<const Telegram> telegram) {
|
||||
// has_update(telegram, wwActivated_, 1); // 0xFF means on
|
||||
// has_update(telegram, wwSelTemp_, 2);
|
||||
has_update(telegram, wwHystOn_, 3); // Hyst on (default -5)
|
||||
has_update(telegram, wwHystOff_, 4); // Hyst off (default -1)
|
||||
has_update(telegram, wwFlowTempOffset_, 5); // default 40
|
||||
has_update(telegram, wwCirc_, 6); // 0xFF means on
|
||||
has_update(telegram, wwCircMode_, 7); // 1=1x3min 6=6x3min 7=continuous
|
||||
has_update(telegram, wwDisinfectionTemp_, 8);
|
||||
// has_bitupdate(telegram, wwChargeType_, 10, 0); // 0 = charge pump, 0xff = 3-way valve
|
||||
}
|
||||
|
||||
|
||||
// 0x1E, only16 bit temperature
|
||||
// Mixer(0x41) -> Boiler(0x08), HydrTemp(0x1E), data: 01 D8
|
||||
void Water::process_IPMHydrTemp(std::shared_ptr<const Telegram> telegram) {
|
||||
has_update(telegram, HydrTemp_, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Settings
|
||||
*/
|
||||
|
||||
bool Water::set_wwSelTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x35, 3, (uint8_t)temperature, 0x34);
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
return false;
|
||||
} else { // SM100
|
||||
write_command(0x7A6, 9, (uint8_t)temperature, 0x7A6);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwMaxTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
return false;
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc_, 10, (uint8_t)temperature, 0x313 + wwc_);
|
||||
} else { // SM100
|
||||
write_command(0x7A6, 8, (uint8_t)temperature, 0x7A6);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwRedTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
return false;
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc_, 5, (uint8_t)temperature, 0x313 + wwc_);
|
||||
} else { // SM100
|
||||
write_command(0x7A6, 10, (uint8_t)temperature, 0x7A6);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwDailyTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7A6, 6, (uint8_t)temperature, 0x7A6);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwDisinfectionTemp(const char * value, const int8_t id) {
|
||||
int temperature;
|
||||
if (!Helpers::value2temperature(value, temperature)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 8, (uint8_t)temperature, 0x33);
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc_, 9, (uint8_t)temperature, 0x313 + wwc_);
|
||||
} else { // SM100
|
||||
write_command(0x7A6, 12, (uint8_t)temperature, 0x7A6);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwCirc(const char * value, const int8_t id) {
|
||||
bool b;
|
||||
if (!Helpers::value2bool(value, b)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 6, b ? 0xFF : 0x00, 0x33);
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x33B + wwc_, 0, b ? 0x01 : 0x00, 0x33B + wwc_);
|
||||
} else { // SM100
|
||||
write_command(0x7A5, 0, b ? 0xFF : 0x00, 0x7A5);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwCircMode(const char * value, const int8_t id) {
|
||||
uint8_t num;
|
||||
if (!Helpers::value2enum(value, num, FL_(enum_wwCircMode))) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_IPM) {
|
||||
write_command(0x33, 7, num, 0x33);
|
||||
} else if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc_, 0, num, 0x313 + wwc_);
|
||||
} else { // SM100
|
||||
write_command(0x7A5, 3, num, 0x7A5);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwKeepWarm(const char * value, const int8_t id) {
|
||||
bool b;
|
||||
if (!Helpers::value2bool(value, b)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x7AE, 0, b ? 0xFF : 0x00, 0x7AE);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwDiffTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc, 7, (int8_t)(v * 10), 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Water::set_wwRequiredTemp(const char * value, const int8_t id) {
|
||||
uint8_t wwc = device_id() - 0x28;
|
||||
float v;
|
||||
if (!Helpers::value2temperature(value, v)) {
|
||||
return false;
|
||||
}
|
||||
if (flags() == EMSdevice::EMS_DEVICE_FLAG_MMPLUS) {
|
||||
write_command(0x313 + wwc, 4, (uint8_t)v, 0x313 + wwc);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
bool Water::set_wwFlowTempOffset(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 5, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwHystOn(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 3, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Water::set_wwHystOff(const char * value, const int8_t id) {
|
||||
int n;
|
||||
if (!Helpers::value2number(value, n)) {
|
||||
return false;
|
||||
}
|
||||
write_command(0x33, 4, n, 0x33);
|
||||
return true;
|
||||
}
|
||||
} // namespace emsesp
|
||||
115
src/devices/water.h
Normal file
115
src/devices/water.h
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* EMS-ESP - https://github.com/emsesp/EMS-ESP
|
||||
* Copyright 2020-2023 Paul Derbyshire
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef EMSESP_WATER_H
|
||||
#define EMSESP_WATER_H
|
||||
|
||||
#include "emsesp.h"
|
||||
|
||||
namespace emsesp {
|
||||
|
||||
class Water : public EMSdevice {
|
||||
public:
|
||||
Water(uint8_t device_type, uint8_t device_id, uint8_t product_id, const char * version, const char * name, uint8_t flags, uint8_t brand);
|
||||
|
||||
private:
|
||||
static uuid::log::Logger logger_;
|
||||
|
||||
uint8_t wwc_;
|
||||
|
||||
// SM100wwTemperature - 0x07D6
|
||||
uint16_t wwTemp_1_;
|
||||
uint16_t wwTemp_2_;
|
||||
uint16_t wwTemp_3_;
|
||||
uint16_t wwTemp_4_;
|
||||
uint16_t wwTemp_5_;
|
||||
uint16_t wwTemp_6_;
|
||||
uint16_t wwTemp_7_;
|
||||
|
||||
// SM100wwStatus - 0x07AA
|
||||
uint8_t wwPump_;
|
||||
|
||||
// SM100wwParam - 0x07A6
|
||||
uint8_t wwMaxTemp_;
|
||||
uint8_t wwSelTemp_;
|
||||
uint8_t wwRedTemp_;
|
||||
uint8_t wwDailyTemp_;
|
||||
uint8_t wwDisinfectionTemp_;
|
||||
|
||||
// SM100wwKeepWarm - 0x07AE
|
||||
uint8_t wwKeepWarm_;
|
||||
|
||||
// SM100wwCirc - 0x07A5
|
||||
uint8_t wwCirc_;
|
||||
uint8_t wwCircMode_;
|
||||
|
||||
// SM100wwStatus2 - 0x07E0
|
||||
uint8_t wwFlow_;
|
||||
uint8_t wwPumpMod_;
|
||||
uint8_t wwStatus2_;
|
||||
|
||||
// mixer
|
||||
uint8_t wwStatus_;
|
||||
uint16_t wwFlowTemp_;
|
||||
int8_t wwDiffTemp_;
|
||||
uint8_t wwRequiredTemp_;
|
||||
|
||||
// IPM
|
||||
uint16_t HydrTemp_;
|
||||
int8_t wwHystOn_; // Hyst on (default -5)
|
||||
int8_t wwHystOff_; // Hyst off (default -1)
|
||||
uint8_t wwFlowTempOffset_; // default 40
|
||||
|
||||
|
||||
void process_SM100wwTemperature(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwStatus(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwStatus2(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwCommand(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwCirc(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwParam(std::shared_ptr<const Telegram> telegram);
|
||||
void process_SM100wwKeepWarm(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
void process_MMPLUSStatusMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSSetMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
void process_MMPLUSConfigMessage_WWC(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
void process_IPMMonitorWW(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMHydrTemp(std::shared_ptr<const Telegram> telegram);
|
||||
void process_IPMParameterWW(std::shared_ptr<const Telegram> telegram);
|
||||
|
||||
|
||||
bool set_wwSelTemp(const char * value, const int8_t id);
|
||||
bool set_wwMaxTemp(const char * value, const int8_t id);
|
||||
bool set_wwRedTemp(const char * value, const int8_t id);
|
||||
bool set_wwCirc(const char * value, const int8_t id);
|
||||
bool set_wwCircMode(const char * value, const int8_t id);
|
||||
bool set_wwKeepWarm(const char * value, const int8_t id);
|
||||
bool set_wwDisinfectionTemp(const char * value, const int8_t id);
|
||||
bool set_wwDailyTemp(const char * value, const int8_t id);
|
||||
|
||||
bool set_wwDiffTemp(const char * value, const int8_t id);
|
||||
bool set_wwRequiredTemp(const char * value, const int8_t id);
|
||||
|
||||
bool set_wwFlowTempOffset(const char * value, const int8_t id);
|
||||
bool set_wwHystOn(const char * value, const int8_t id);
|
||||
bool set_wwHystOff(const char * value, const int8_t id);
|
||||
};
|
||||
|
||||
} // namespace emsesp
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user