From 002bc266eb8c61455424cd8d5f5e93679837264d Mon Sep 17 00:00:00 2001
From: Stephan Hadinger
Date: Wed, 27 Apr 2022 09:40:56 +0200
Subject: [PATCH 01/52] Berry improve logging when using `load()`
---
lib/libesp32/berry/generate/be_const_strtab.h | 2 +-
.../berry/generate/be_const_strtab_def.h | 6 +--
.../berry_tasmota/src/be_tasmota_lib.c | 37 ++++++++++---------
.../berry_tasmota/src/embedded/Tasmota.be | 4 +-
4 files changed, 25 insertions(+), 24 deletions(-)
diff --git a/lib/libesp32/berry/generate/be_const_strtab.h b/lib/libesp32/berry/generate/be_const_strtab.h
index 26d4948b0..d4c016e07 100644
--- a/lib/libesp32/berry/generate/be_const_strtab.h
+++ b/lib/libesp32/berry/generate/be_const_strtab.h
@@ -21,7 +21,7 @@ extern const bcstring be_const_str_BRY_X3A_X20argument_X20must_X20be_X20a_X20fun
extern const bcstring be_const_str_BRY_X3A_X20bytecode_X20has_X20wrong_X20version_X20_X27_X25s_X27_X20_X28_X25i_X29;
extern const bcstring be_const_str_BRY_X3A_X20corrupt_X20bytecode_X20_X27_X25s_X27;
extern const bcstring be_const_str_BRY_X3A_X20could_X20not_X20save_X20compiled_X20file_X20_X25s_X20_X28_X25s_X29;
-extern const bcstring be_const_str_BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X29;
+extern const bcstring be_const_str_BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X20_X2D_X20_X25s_X29;
extern const bcstring be_const_str_BRY_X3A_X20failed_X20to_X20load_X20_persist_X2Ejson;
extern const bcstring be_const_str_BRY_X3A_X20failed_X20to_X20load_X20compiled_X20_X27_X25s_X27_X20_X28_X25s_X29;
extern const bcstring be_const_str_BRY_X3A_X20failed_X20to_X20run_X20compiled_X20code_X20_X27_X25s_X27_X20_X2D_X20_X25s;
diff --git a/lib/libesp32/berry/generate/be_const_strtab_def.h b/lib/libesp32/berry/generate/be_const_strtab_def.h
index d2c51ccaf..23aceb41b 100644
--- a/lib/libesp32/berry/generate/be_const_strtab_def.h
+++ b/lib/libesp32/berry/generate/be_const_strtab_def.h
@@ -95,7 +95,7 @@ be_define_const_str(BRY_X3A_X20argument_X20must_X20be_X20a_X20function, "BRY: ar
be_define_const_str(BRY_X3A_X20bytecode_X20has_X20wrong_X20version_X20_X27_X25s_X27_X20_X28_X25i_X29, "BRY: bytecode has wrong version '%s' (%i)", 2140321415u, 0, 41, &be_const_str_clock);
be_define_const_str(BRY_X3A_X20corrupt_X20bytecode_X20_X27_X25s_X27, "BRY: corrupt bytecode '%s'", 4009923544u, 0, 26, &be_const_str_codedump);
be_define_const_str(BRY_X3A_X20could_X20not_X20save_X20compiled_X20file_X20_X25s_X20_X28_X25s_X29, "BRY: could not save compiled file %s (%s)", 736659787u, 0, 41, &be_const_str_clock_icon);
-be_define_const_str(BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X29, "BRY: failed to load '%s' (%s)", 54995609u, 0, 29, &be_const_str__rules);
+be_define_const_str(BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X20_X2D_X20_X25s_X29, "BRY: failed to load '%s' (%s - %s)", 1047433014u, 0, 34, &be_const_str_couldn_X27t_X20not_X20initialize_X20noepixelbus);
be_define_const_str(BRY_X3A_X20failed_X20to_X20load_X20_persist_X2Ejson, "BRY: failed to load _persist.json", 2991913445u, 0, 33, &be_const_str__global_def);
be_define_const_str(BRY_X3A_X20failed_X20to_X20load_X20compiled_X20_X27_X25s_X27_X20_X28_X25s_X29, "BRY: failed to load compiled '%s' (%s)", 3488122666u, 0, 38, &be_const_str_connection_error);
be_define_const_str(BRY_X3A_X20failed_X20to_X20run_X20compiled_X20code_X20_X27_X25s_X27_X20_X2D_X20_X25s, "BRY: failed to run compiled code '%s' - %s", 380265962u, 0, 42, &be_const_str_gpio);
@@ -1109,8 +1109,8 @@ static const bstring* const m_string_table[] = {
(const bstring *)&be_const_str_coord_arr,
(const bstring *)&be_const_str_CFG_X3A_X20multiple_X20autoconf_X20files_X20found_X2C_X20aborting_X20_X28_X27_X25s_X27_X20_X2B_X20_X27_X25s_X27_X29,
(const bstring *)&be_const_str_line_dsc,
- (const bstring *)&be_const_str_BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X29,
- (const bstring *)&be_const_str_couldn_X27t_X20not_X20initialize_X20noepixelbus,
+ (const bstring *)&be_const_str__rules,
+ (const bstring *)&be_const_str_BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X20_X2D_X20_X25s_X29,
(const bstring *)&be_const_str__X3A,
NULL,
(const bstring *)&be_const_str_CFG_X3A_X20loading_X20_X27_X25s_X27,
diff --git a/lib/libesp32/berry_tasmota/src/be_tasmota_lib.c b/lib/libesp32/berry_tasmota/src/be_tasmota_lib.c
index 0e496d7f4..cec5ddd5d 100644
--- a/lib/libesp32/berry_tasmota/src/be_tasmota_lib.c
+++ b/lib/libesp32/berry_tasmota/src/be_tasmota_lib.c
@@ -1365,7 +1365,7 @@ be_local_closure(Tasmota_load, /* name */
})
),
be_nested_proto(
- 9, /* nstack */
+ 11, /* nstack */
1, /* argc */
0, /* varg */
0, /* has upvals */
@@ -1377,11 +1377,11 @@ be_local_closure(Tasmota_load, /* name */
/* K0 */ be_nested_str(file),
/* K1 */ be_nested_str(string),
/* K2 */ be_nested_str(format),
- /* K3 */ be_nested_str(BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X29),
+ /* K3 */ be_nested_str(BRY_X3A_X20failed_X20to_X20load_X20_X27_X25s_X27_X20_X28_X25s_X20_X2D_X20_X25s_X29),
}),
&be_const_str_try_compile,
&be_const_str_solidified,
- ( &(const binstruction[23]) { /* code */
+ ( &(const binstruction[24]) { /* code */
0xA8020007, // 0000 EXBLK 0 #0009
0x6004000D, // 0001 GETGBL R1 G13
0x5C080000, // 0002 MOVE R2 R0
@@ -1390,21 +1390,22 @@ be_local_closure(Tasmota_load, /* name */
0xA8040001, // 0005 EXBLK 1 1
0x80040200, // 0006 RET 1 R1
0xA8040001, // 0007 EXBLK 1 1
- 0x7002000B, // 0008 JMP #0015
- 0xAC040001, // 0009 CATCH R1 0 1
- 0x70020008, // 000A JMP #0014
- 0xA40A0200, // 000B IMPORT R2 K1
- 0x600C0001, // 000C GETGBL R3 G1
- 0x8C100502, // 000D GETMET R4 R2 K2
- 0x58180003, // 000E LDCONST R6 K3
- 0x5C1C0000, // 000F MOVE R7 R0
- 0x5C200200, // 0010 MOVE R8 R1
- 0x7C100800, // 0011 CALL R4 4
- 0x7C0C0200, // 0012 CALL R3 1
- 0x70020000, // 0013 JMP #0015
- 0xB0080000, // 0014 RAISE 2 R0 R0
- 0x4C040000, // 0015 LDNIL R1
- 0x80040200, // 0016 RET 1 R1
+ 0x7002000C, // 0008 JMP #0016
+ 0xAC040002, // 0009 CATCH R1 0 2
+ 0x70020009, // 000A JMP #0015
+ 0xA40E0200, // 000B IMPORT R3 K1
+ 0x60100001, // 000C GETGBL R4 G1
+ 0x8C140702, // 000D GETMET R5 R3 K2
+ 0x581C0003, // 000E LDCONST R7 K3
+ 0x5C200000, // 000F MOVE R8 R0
+ 0x5C240200, // 0010 MOVE R9 R1
+ 0x5C280400, // 0011 MOVE R10 R2
+ 0x7C140A00, // 0012 CALL R5 5
+ 0x7C100200, // 0013 CALL R4 1
+ 0x70020000, // 0014 JMP #0016
+ 0xB0080000, // 0015 RAISE 2 R0 R0
+ 0x4C040000, // 0016 LDNIL R1
+ 0x80040200, // 0017 RET 1 R1
})
),
be_nested_proto(
diff --git a/lib/libesp32/berry_tasmota/src/embedded/Tasmota.be b/lib/libesp32/berry_tasmota/src/embedded/Tasmota.be
index 60fc6a77f..52e6a1e47 100644
--- a/lib/libesp32/berry_tasmota/src/embedded/Tasmota.be
+++ b/lib/libesp32/berry_tasmota/src/embedded/Tasmota.be
@@ -464,9 +464,9 @@ class Tasmota
try
var compiled = compile(f_name, 'file')
return compiled
- except .. as e
+ except .. as e, m
import string
- print(string.format('BRY: failed to load \'%s\' (%s)',f_name,e))
+ print(string.format('BRY: failed to load \'%s\' (%s - %s)',f_name,e,m))
end
return nil
end
From d7d71cd9c858a8cd521f47b03c4027d86b9f2b63 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Fri, 22 Apr 2022 08:40:29 +0200
Subject: [PATCH 02/52] Add flowmeter (YF-DN50 and similary)
---
CHANGELOG.md | 1 +
tasmota/berry/include/be_gpio_defines.h | 1 +
tasmota/i18n.h | 1 +
tasmota/language/af_AF.h | 9 +-
tasmota/language/bg_BG.h | 9 +-
tasmota/language/cs_CZ.h | 9 +-
tasmota/language/de_DE.h | 9 +-
tasmota/language/el_GR.h | 9 +-
tasmota/language/en_GB.h | 7 +
tasmota/language/es_ES.h | 9 +-
tasmota/language/fr_FR.h | 9 +-
tasmota/language/fy_NL.h | 9 +-
tasmota/language/he_HE.h | 9 +-
tasmota/language/hu_HU.h | 6 +
tasmota/language/it_IT.h | 6 +
tasmota/language/ko_KO.h | 9 +-
tasmota/language/nl_NL.h | 9 +-
tasmota/language/pl_PL.h | 9 +-
tasmota/language/pt_BR.h | 9 +-
tasmota/language/pt_PT.h | 9 +-
tasmota/language/ro_RO.h | 9 +-
tasmota/language/ru_RU.h | 9 +-
tasmota/language/sk_SK.h | 9 +-
tasmota/language/sv_SE.h | 9 +-
tasmota/language/tr_TR.h | 9 +-
tasmota/language/uk_UA.h | 9 +-
tasmota/language/vi_VN.h | 9 +-
tasmota/language/zh_CN.h | 9 +-
tasmota/language/zh_TW.h | 9 +-
tasmota/settings.h | 6 +-
tasmota/tasmota_template.h | 8 +
tasmota/xsns_96_flowmeter.ino | 257 ++++++++++++++++++++++++
tools/lv_gpio/lv_gpio_enum.h | 2 +
33 files changed, 476 insertions(+), 26 deletions(-)
create mode 100644 tasmota/xsns_96_flowmeter.ino
diff --git a/CHANGELOG.md b/CHANGELOG.md
index b4fafaadc..a74756c3a 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -11,6 +11,7 @@ All notable changes to this project will be documented in this file.
- Command ``EnergyExportActive`` to (p)reset energy export active for supported devices. Currently ADE7880 only (#13515)
- Sonoff SPM delayed SetPowerOnState (#13447)
- Command ``SetOption139 0/1`` to switch between pressure unit "mmHg" (0) or "inHg" (1) when ``SO24 1`` (#15350)
+- Support for flow meter
### Changed
diff --git a/tasmota/berry/include/be_gpio_defines.h b/tasmota/berry/include/be_gpio_defines.h
index ec2271073..b6431945f 100644
--- a/tasmota/berry/include/be_gpio_defines.h
+++ b/tasmota/berry/include/be_gpio_defines.h
@@ -73,6 +73,7 @@ const be_const_member_t lv_gpio_constants[] = {
{ "ETH_PHY_POWER", (int32_t) GPIO_ETH_PHY_POWER },
{ "EXS_ENABLE", (int32_t) GPIO_EXS_ENABLE },
{ "FALLING", FALLING },
+ { "FLOWMETER_SIGNAL", (int32_t) GPIO_FLOWMETER_IN },
{ "FTC532", (int32_t) GPIO_FTC532 },
{ "GPS_RX", (int32_t) GPIO_GPS_RX },
{ "GPS_TX", (int32_t) GPIO_GPS_TX },
diff --git a/tasmota/i18n.h b/tasmota/i18n.h
index 473bd8b4a..a36001ac9 100644
--- a/tasmota/i18n.h
+++ b/tasmota/i18n.h
@@ -225,6 +225,7 @@
#define D_JSON_RESETTABLE_TOTAL_ACTIVE "ResetTotalActive"
#define D_JSON_SIGNALSTRENGTH "SignalStrength"
#define D_JSON_CHIPTEMPERATURE "ChipTemperature"
+#define D_JSON_FLOW_UNIT "FLowUnit"
#define D_RSLT_ENERGY "ENERGY"
#define D_RSLT_HASS_STATE "HASS_STATE"
diff --git a/tasmota/language/af_AF.h b/tasmota/language/af_AF.h
index 6c7934f76..32b04c81c 100644
--- a/tasmota/language/af_AF.h
+++ b/tasmota/language/af_AF.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Wagwoord geverifieer" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fout" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/bg_BG.h b/tasmota/language/bg_BG.h
index 1e6270266..f36280949 100644
--- a/tasmota/language/bg_BG.h
+++ b/tasmota/language/bg_BG.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Грешка" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/cs_CZ.h b/tasmota/language/cs_CZ.h
index 941dd24a2..32bcea496 100644
--- a/tasmota/language/cs_CZ.h
+++ b/tasmota/language/cs_CZ.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/de_DE.h b/tasmota/language/de_DE.h
index 9218e9537..c82ea0864 100644
--- a/tasmota/language/de_DE.h
+++ b/tasmota/language/de_DE.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Neue Adresse"
#define D_OUT_OF_RANGE "Außerhalb Bereich"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Übereinstimmung" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fehler" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/el_GR.h b/tasmota/language/el_GR.h
index 67481f5a2..2115df377 100644
--- a/tasmota/language/el_GR.h
+++ b/tasmota/language/el_GR.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/en_GB.h b/tasmota/language/en_GB.h
index afa9b3a8f..991b51d60 100644
--- a/tasmota/language/en_GB.h
+++ b/tasmota/language/en_GB.h
@@ -866,6 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/es_ES.h b/tasmota/language/es_ES.h
index b93135578..e6a61f1af 100644
--- a/tasmota/language/es_ES.h
+++ b/tasmota/language/es_ES.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Cambiando dirección a"
#define D_OUT_OF_RANGE "Fuera de Rango"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Clave Correcta" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/fr_FR.h b/tasmota/language/fr_FR.h
index 5638233b1..56781aaf5 100644
--- a/tasmota/language/fr_FR.h
+++ b/tasmota/language/fr_FR.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Positionner l'adresse à"
#define D_OUT_OF_RANGE "Hors limites"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Mot-de-passe vérifié" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Erreur" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/fy_NL.h b/tasmota/language/fy_NL.h
index fc97068d3..a758a583e 100644
--- a/tasmota/language/fy_NL.h
+++ b/tasmota/language/fy_NL.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/he_HE.h b/tasmota/language/he_HE.h
index dc7be8aa0..043401686 100644
--- a/tasmota/language/he_HE.h
+++ b/tasmota/language/he_HE.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/hu_HU.h b/tasmota/language/hu_HU.h
index 04b069358..0eb7d874d 100644
--- a/tasmota/language/hu_HU.h
+++ b/tasmota/language/hu_HU.h
@@ -913,6 +913,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1056,10 @@
#define D_FP_PASSVERIFY "Jelszó ellenőrizve" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Hiba" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/it_IT.h b/tasmota/language/it_IT.h
index 769f43241..7e7ab8830 100644
--- a/tasmota/language/it_IT.h
+++ b/tasmota/language/it_IT.h
@@ -913,6 +913,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Imposta indirizzo a"
#define D_OUT_OF_RANGE "Fuori intervallo"
@@ -1054,6 +1056,10 @@
#define D_FP_PASSVERIFY "Password verificata" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Errore" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/ko_KO.h b/tasmota/language/ko_KO.h
index 2716feea4..de24ea75e 100644
--- a/tasmota/language/ko_KO.h
+++ b/tasmota/language/ko_KO.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/nl_NL.h b/tasmota/language/nl_NL.h
index a7a1e383a..d7db56006 100644
--- a/tasmota/language/nl_NL.h
+++ b/tasmota/language/nl_NL.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Nieuw adres"
#define D_OUT_OF_RANGE "Buiten beriek"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Wachtwoord herkend" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fout" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/pl_PL.h b/tasmota/language/pl_PL.h
index 6bec6b159..9c6532741 100644
--- a/tasmota/language/pl_PL.h
+++ b/tasmota/language/pl_PL.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Ustawiam adres na"
#define D_OUT_OF_RANGE "Poza zakresem"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Zweryfikowano poprawnie" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Błąd" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/pt_BR.h b/tasmota/language/pt_BR.h
index 15b574f64..ba1b8d5d4 100644
--- a/tasmota/language/pt_BR.h
+++ b/tasmota/language/pt_BR.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "W/h"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Mudança de endereço para"
#define D_OUT_OF_RANGE "Fora de Alcance"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Senha verificada" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Erro" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/pt_PT.h b/tasmota/language/pt_PT.h
index b664cf3cf..1ac353e61 100644
--- a/tasmota/language/pt_PT.h
+++ b/tasmota/language/pt_PT.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Mudança de endereço para"
#define D_OUT_OF_RANGE "Fora de Alcance"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/ro_RO.h b/tasmota/language/ro_RO.h
index cb709f185..bc28c0959 100644
--- a/tasmota/language/ro_RO.h
+++ b/tasmota/language/ro_RO.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/ru_RU.h b/tasmota/language/ru_RU.h
index e45388a22..713dca26f 100644
--- a/tasmota/language/ru_RU.h
+++ b/tasmota/language/ru_RU.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "А"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "Вт"
#define D_UNIT_WATTHOUR "ВтЧ"
#define D_UNIT_WATT_METER_QUADRAT "Вт/м²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/sk_SK.h b/tasmota/language/sk_SK.h
index d376dc26c..17bc2c417 100644
--- a/tasmota/language/sk_SK.h
+++ b/tasmota/language/sk_SK.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/sv_SE.h b/tasmota/language/sv_SE.h
index dbd138ff5..28d584288 100644
--- a/tasmota/language/sv_SE.h
+++ b/tasmota/language/sv_SE.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/tr_TR.h b/tasmota/language/tr_TR.h
index bcb341725..e05adff5b 100644
--- a/tasmota/language/tr_TR.h
+++ b/tasmota/language/tr_TR.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/uk_UA.h b/tasmota/language/uk_UA.h
index b13930560..8022a2302 100644
--- a/tasmota/language/uk_UA.h
+++ b/tasmota/language/uk_UA.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "А"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "Вт"
#define D_UNIT_WATTHOUR "Вт/г"
#define D_UNIT_WATT_METER_QUADRAT "Вт/м²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/vi_VN.h b/tasmota/language/vi_VN.h
index 0f4e5f563..f04d1196e 100644
--- a/tasmota/language/vi_VN.h
+++ b/tasmota/language/vi_VN.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/zh_CN.h b/tasmota/language/zh_CN.h
index 89ad958ca..d209c207c 100644
--- a/tasmota/language/zh_CN.h
+++ b/tasmota/language/zh_CN.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "A"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "W"
#define D_UNIT_WATTHOUR "Wh"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/language/zh_TW.h b/tasmota/language/zh_TW.h
index 767df5857..3cf448b2e 100644
--- a/tasmota/language/zh_TW.h
+++ b/tasmota/language/zh_TW.h
@@ -865,7 +865,8 @@
#define D_GPIO_SHIFT595_OE "74x595 OE"
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
-#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWMETER "Flowmeter"
// Units
#define D_UNIT_AMPERE "安培"
@@ -913,6 +914,8 @@
#define D_UNIT_WATT "瓦特"
#define D_UNIT_WATTHOUR "瓦小時"
#define D_UNIT_WATT_METER_QUADRAT "W/m²"
+#define D_UNIT_LITER_PER_MINUTE "l/min"
+#define D_UNIT_CUBICMETER_PER_HOUR "m³/h"
#define D_NEW_ADDRESS "Setting address to"
#define D_OUT_OF_RANGE "Out of Range"
@@ -1054,6 +1057,10 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
+// xsns_96_flowmeter.ino
+#define D_FLOWMETER_NAME "Flowmeter"
+#define D_FLOWMETER_RATE "Rate"
+
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
#define D_NEOPOOL_MACH_HIDROLIFE "Hidrolife"
diff --git a/tasmota/settings.h b/tasmota/settings.h
index f8b961527..264b50494 100644
--- a/tasmota/settings.h
+++ b/tasmota/settings.h
@@ -351,7 +351,7 @@ typedef union {
uint8_t data;
struct {
uint8_t spare0 : 1;
- uint8_t spare1 : 1;
+ uint8_t flowmeter_unit : 1; // Sensor96 9,x - unit l/min (0) or m³/h (1)
uint8_t bh1750_2_resolution : 2;
uint8_t bh1750_1_resolution : 2; // Sensor10 1,2,3
uint8_t hx711_json_weight_change : 1; // Sensor34 8,x - Enable JSON message on weight change
@@ -779,10 +779,10 @@ typedef struct {
uint8_t tcp_config; // F5F
uint8_t light_step_pixels; // F60
- uint8_t free_f61[27]; // F61 - Decrement if adding new Setting variables just above and below
+ uint8_t free_f61[23]; // F61 - Decrement if adding new Setting variables just above and below
// Only 32 bit boundary variables below
-
+ uint16_t flowmeter_calibration[2]; // F78
int32_t energy_kWhexport_ph[3]; // F7C
uint32_t eth_ipv4_address[5]; // F88
uint32_t energy_kWhtotal; // F9C
diff --git a/tasmota/tasmota_template.h b/tasmota/tasmota_template.h
index b576027b3..0a8f428dc 100644
--- a/tasmota/tasmota_template.h
+++ b/tasmota/tasmota_template.h
@@ -187,6 +187,7 @@ enum UserSelectablePins {
GPIO_RESET, // Generic reset
GPIO_MS01, // Sonoff MS01 Moisture Sensor 1wire interface
GPIO_SDIO_CMD, GPIO_SDIO_CLK, GPIO_SDIO_D0, GPIO_SDIO_D1, GPIO_SDIO_D2, GPIO_SDIO_D3, // SD Card SDIO interface, including 1-bit and 4-bit modes
+ GPIO_FLOWMETER_IN, // Flow Meter Pin
GPIO_SENSOR_END };
enum ProgramSelectablePins {
@@ -418,12 +419,14 @@ const char kSensorNames[] PROGMEM =
D_SENSOR_SDIO_D1 "|"
D_SENSOR_SDIO_D2 "|"
D_SENSOR_SDIO_D3 "|"
+ D_SENSOR_FLOWMETER "|"
;
const char kSensorNamesFixed[] PROGMEM =
D_SENSOR_USER;
#define MAX_MAX31865S 6
+#define MAX_FLOWMETER 2
#define MAX_A4988_MSS 3
#define MAX_WEBCAM_DATA 8
#define MAX_WEBCAM_HSD 3
@@ -973,6 +976,11 @@ const uint16_t kGpioNiceList[] PROGMEM = {
AGPIO(GPIO_CM11_TXD), // CM110x Serial interface
AGPIO(GPIO_CM11_RXD), // CM110x Serial interface
#endif
+
+#if defined(USE_FLOWMETER)
+ AGPIO(GPIO_FLOWMETER_IN) + MAX_FLOWMETER, // Flow meter Pin
+#endif
+
/*-------------------------------------------------------------------------------------------*\
* ESP32 specifics
\*-------------------------------------------------------------------------------------------*/
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
new file mode 100644
index 000000000..80478e125
--- /dev/null
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -0,0 +1,257 @@
+/*
+ xsns_96_flowmeter.ino - flowmeter support for Tasmota
+ Up to two flowmeter YF-DN50 and similary supported
+ (f = 1 Hz up to 5 kHz)
+
+ Copyright (C) 2022 Norbert Richter
+
+ 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 .
+*/
+
+#ifdef USE_FLOWMETER
+
+#define XSNS_96 96
+
+#define FLOWMETER_WEIGHT_AVG_SAMPLE 20 // samples
+#define FLOWMETER_MIN_FREQ 1 // Hz
+
+// The Arduino standard GPIO routines are not enough,
+// must use some from the Espressif SDK as well
+extern "C" {
+#include "gpio.h"
+}
+
+
+#ifdef USE_WEBSERVER
+const char HTTP_SNS_FLOWMETER[] PROGMEM =
+ "{s}" D_FLOWMETER_NAME "-%d " D_FLOWMETER_RATE "{m}%*_f %s{e}"
+ ;
+#endif // USE_WEBSERVER
+
+
+int32_t flowmeter_period[MAX_FLOWMETER] = {0};
+float flowmeter_period_avg[MAX_FLOWMETER] = {0};
+uint32_t flowmeter_count[MAX_FLOWMETER] = {0};
+volatile uint32_t flowmeter_last_irq[MAX_FLOWMETER] = {0};
+
+bool flowmeter_valuesread = false;
+
+
+void IRAM_ATTR FlowMeterIR(uint16_t irq)
+{
+ uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
+ GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
+ uint32_t time = micros();
+ uint32_t i = irq;
+ if (irq < MAX_FLOWMETER) {
+ if ((time - flowmeter_last_irq[i]) < (1000000 / FLOWMETER_MIN_FREQ)) {
+ flowmeter_period[i] = time - flowmeter_last_irq[i];
+ } else {
+ flowmeter_period[i] = 0;
+ }
+ flowmeter_valuesread = true;
+ flowmeter_last_irq[i] = time;
+ }
+}
+// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way:
+void IRAM_ATTR FlowMeter1IR(void)
+{
+ FlowMeterIR(0);
+}
+void IRAM_ATTR FlowMeter2IR(void)
+{
+ FlowMeterIR(1);
+}
+
+void FlowMeterRead(void)
+{
+ for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
+ if ((micros() - flowmeter_last_irq[i]) >= (1000000 / FLOWMETER_MIN_FREQ)) {
+ flowmeter_period[i] = 0;
+ flowmeter_period_avg[i] = 0;
+ }
+
+ // exponentially weighted average
+ if (flowmeter_count[i] <= FLOWMETER_WEIGHT_AVG_SAMPLE) {
+ flowmeter_count[i]++;
+ }
+ flowmeter_period_avg[i] -= flowmeter_period_avg[i] / flowmeter_count[i];
+ flowmeter_period_avg[i] += float(flowmeter_period[i]) / flowmeter_count[i];
+ }
+}
+
+void FlowMeterInit(void)
+{
+ void (* irq_service[MAX_FLOWMETER])(void)= {FlowMeter1IR, FlowMeter2IR};
+
+ flowmeter_valuesread = false;
+ for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
+ pinMode(Pin(GPIO_FLOWMETER_IN, i), INPUT);
+ attachInterrupt(Pin(GPIO_FLOWMETER_IN, i), irq_service[i], RISING);
+ }
+}
+
+void FlowMeterShow(bool json)
+{
+ for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
+ float flowmeter_period_float = 0;
+ float flowmeter_rate_float = 0;
+ float flowmeter_period_avg_float = 0;
+ float flowmeter_rate_avg_float = 0;
+ float flowmeter_factor = 1.0;
+ float flowmeter_unit_factor = Settings->SensorBits1.flowmeter_unit ? 500 : 8333;;
+
+ if (Settings->flowmeter_calibration[i]) {
+ flowmeter_factor = (float)Settings->flowmeter_calibration[i] / 1000;
+ }
+
+ if (flowmeter_period[i]) {
+ flowmeter_period_float = (float)flowmeter_period[i] / 1000;
+ flowmeter_period_avg_float = flowmeter_period_avg[i] / 1000;
+
+ flowmeter_rate_float = flowmeter_unit_factor / (float)flowmeter_period[i] * (flowmeter_factor * 1000);
+ flowmeter_rate_avg_float = flowmeter_unit_factor / flowmeter_period_avg[i] * (flowmeter_factor * 1000);
+ }
+
+ if (PinUsed(GPIO_FLOWMETER_IN, i)) {
+ if (json) {
+ ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "-%d\":{\"" D_JSON_PERIOD "\":%*_f,\"" D_JSON_FLOWRATE "\":%*_f}"),
+ i+1,
+ Settings->flag2.frequency_resolution, &flowmeter_period_float,
+ Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float
+ );
+#ifdef USE_WEBSERVER
+ } else {
+ WSContentSend_PD(HTTP_SNS_FLOWMETER,
+ i+1,
+ Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float,
+ Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ );
+#endif // USE_WEBSERVER
+ }
+ }
+ if (json) {
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOW_UNIT "\":\"%s\""),
+ Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ );
+ }
+ }
+}
+
+
+
+/*********************************************************************************************\
+ * Supported commands for Sensor96:
+ *
+ * Sensor96 - Show current settings
+ * Sensor96 1 - Set sensor 1 factor (x 1000) - to set to 0.2 enter 'Sensor96 1 200'
+ * Sensor96 2 - Set sensor 2 factor (x 1000)
+ * Sensor96 9 0|1 - Show flow value in l/min (0) or m³/h (1)
+ *
+ * Flowmeter calibration:
+ * - get the current displayed flow rate (D)
+ * - get the current (c)
+ * - measure the real flow rate (M)
+ * - new = M / (c * D)
+ *
+ * Example:
+ * - displayed flow rate = 254.39 l/min (D)
+ * - current = 1.0 (c)
+ * - real flow rate = 83.42 l/min (M)
+ *
+ * new = M / (c * D) = 83.42 / (1 * 254.39) = 0.328
+ * Cmd: Sensor96 x 328
+\*********************************************************************************************/
+
+bool FlowMeterCommand(void) {
+ bool show_parms = true;
+ char argument[XdrvMailbox.data_len];
+
+ long value = 0;
+ for (uint32_t ca = 0; ca < XdrvMailbox.data_len; ca++) {
+ if ((' ' == XdrvMailbox.data[ca]) || ('=' == XdrvMailbox.data[ca])) { XdrvMailbox.data[ca] = ','; }
+ }
+ bool any_value = (strchr(XdrvMailbox.data, ',') != nullptr);
+ if (any_value) {
+ value = strtol(ArgV(argument, 2), nullptr, 10);
+ }
+
+ switch (XdrvMailbox.payload) {
+ case 1: // Calibration value
+ case 2: // Calibration value
+ if (any_value) {
+ Settings->flowmeter_calibration[XdrvMailbox.payload - 1] = value;
+ ResponseCmndNumber(value);
+ show_parms = false;
+ }
+ break;
+ case 9: // Unit
+ if (any_value) {
+ Settings->SensorBits1.flowmeter_unit = value & 1;
+ ResponseCmndNumber(value & 1);
+ show_parms = false;
+ }
+ break;
+ }
+
+ if (show_parms) {
+ Response_P(PSTR("{\"Sensor%d\":{"), XSNS_96);
+ for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
+ float flowmeter_factor = Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] / 1000 : 1.0;
+ ResponseAppend_P(PSTR("\"" D_JSON_POWERFACTOR "-%d\":%3_f,"), i+1, &flowmeter_factor);
+ }
+ ResponseAppend_P(PSTR("\"" D_JSON_FLOW_UNIT "\":\"%s\"}}"),
+ Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ );
+ }
+
+ return true;
+}
+
+/*********************************************************************************************\
+ * Interface
+\*********************************************************************************************/
+
+bool Xsns96(uint8_t function)
+{
+ bool result = false;
+
+ if (PinUsed(GPIO_FLOWMETER_IN, GPIO_ANY)) {
+ switch (function) {
+ case FUNC_INIT:
+ FlowMeterInit();
+ break;
+ case FUNC_EVERY_250_MSECOND:
+ FlowMeterRead();
+ break;
+ case FUNC_COMMAND_SENSOR:
+ if (XSNS_96 == XdrvMailbox.index) {
+ result = FlowMeterCommand();
+ }
+ break;
+ case FUNC_JSON_APPEND:
+ FlowMeterShow(true);
+ break;
+#ifdef USE_WEBSERVER
+ case FUNC_WEB_SENSOR:
+ FlowMeterShow(false);
+ break;
+#endif // USE_WEBSERVER
+
+ }
+ }
+ return result;
+}
+
+#endif // USE_FLOWMETER
diff --git a/tools/lv_gpio/lv_gpio_enum.h b/tools/lv_gpio/lv_gpio_enum.h
index 19e517add..f6ded405d 100644
--- a/tools/lv_gpio/lv_gpio_enum.h
+++ b/tools/lv_gpio/lv_gpio_enum.h
@@ -299,4 +299,6 @@ BL6523_RX = GPIO_BL6523_RX
ADE7880_IRQ = GPIO_ADE7880_IRQ
RESET = GPIO_RESET
+FLOWMETER_SIGNAL = GPIO_FLOWMETER_IN
+
SENSOR_END = GPIO_SENSOR_END
From abc4f74fbcbaa722f11e7ad0c935a1dc7ba5ac43 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Tue, 26 Apr 2022 14:52:26 +0200
Subject: [PATCH 03/52] Refactor flowmeter calc
---
tasmota/xsns_96_flowmeter.ino | 29 ++++++++---------------------
1 file changed, 8 insertions(+), 21 deletions(-)
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index 80478e125..1923fb6e9 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -105,30 +105,17 @@ void FlowMeterInit(void)
void FlowMeterShow(bool json)
{
for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- float flowmeter_period_float = 0;
- float flowmeter_rate_float = 0;
- float flowmeter_period_avg_float = 0;
float flowmeter_rate_avg_float = 0;
- float flowmeter_factor = 1.0;
- float flowmeter_unit_factor = Settings->SensorBits1.flowmeter_unit ? 500 : 8333;;
-
- if (Settings->flowmeter_calibration[i]) {
- flowmeter_factor = (float)Settings->flowmeter_calibration[i] / 1000;
- }
if (flowmeter_period[i]) {
- flowmeter_period_float = (float)flowmeter_period[i] / 1000;
- flowmeter_period_avg_float = flowmeter_period_avg[i] / 1000;
-
- flowmeter_rate_float = flowmeter_unit_factor / (float)flowmeter_period[i] * (flowmeter_factor * 1000);
- flowmeter_rate_avg_float = flowmeter_unit_factor / flowmeter_period_avg[i] * (flowmeter_factor * 1000);
+ flowmeter_rate_avg_float =
+ ((Settings->SensorBits1.flowmeter_unit ? (1000000.0 / 1000.0) : (1000000 / 60.0)) / 2.0) / flowmeter_period_avg[i] * (Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] : 1000.0);
}
if (PinUsed(GPIO_FLOWMETER_IN, i)) {
if (json) {
- ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "-%d\":{\"" D_JSON_PERIOD "\":%*_f,\"" D_JSON_FLOWRATE "\":%*_f}"),
+ ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "-%d\":{\"" D_JSON_FLOWRATE "\":%*_f}"),
i+1,
- Settings->flag2.frequency_resolution, &flowmeter_period_float,
Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float
);
#ifdef USE_WEBSERVER
@@ -141,11 +128,11 @@ void FlowMeterShow(bool json)
#endif // USE_WEBSERVER
}
}
- if (json) {
- ResponseAppend_P(PSTR(",\"" D_JSON_FLOW_UNIT "\":\"%s\""),
- Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
- );
- }
+ }
+ if (json) {
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOW_UNIT "\":\"%s\""),
+ Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ );
}
}
From fb796187c2baba3843b61e12d3e758d7dfadda9b Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 08:20:30 +0200
Subject: [PATCH 04/52] Flowmeter integration
---
BUILDS.md | 1 +
tasmota/my_user_config.h | 2 ++
tasmota/support_features.ino | 4 +++-
3 files changed, 6 insertions(+), 1 deletion(-)
diff --git a/BUILDS.md b/BUILDS.md
index 44b82d93a..4b3681d80 100644
--- a/BUILDS.md
+++ b/BUILDS.md
@@ -216,6 +216,7 @@ Note: `minimal` variant is not listed as it shouldn't be used outside of the [up
| USE_HRE | - | - / x | - | x | - | - |
| USE_A4988_STEPPER | - | - / - | - | - | - | - |
| USE_NEOPOOL | - | - / - | - | - | - | - |
+| USE_FLOWMETER | - | - / - | - | - | - | - |
| | | | | | | |
| Feature or Sensor | l | t | k | s | i | d | Remarks
| USE_DISPLAY | - | - / - | - | - | - | x |
diff --git a/tasmota/my_user_config.h b/tasmota/my_user_config.h
index 6a197c5d5..3fdeca42c 100644
--- a/tasmota/my_user_config.h
+++ b/tasmota/my_user_config.h
@@ -948,6 +948,8 @@
//#define USE_NEOPOOL // Add support for Sugar Valley NeoPool Controller - also known under brands Hidrolife, Aquascenic, Oxilife, Bionet, Hidroniser, UVScenic, Station, Brilix, Bayrol and Hay (+6k flash, +60 mem)
// #define NEOPOOL_MODBUS_ADDRESS 1 // Any modbus address
+//#define FLOWMETER // Add support for water flow meter YF-DN50 and similary (+1k5 code)
+
// -- Thermostat control ----------------------------
//#define USE_THERMOSTAT // Add support for Thermostat
#define THERMOSTAT_CONTROLLER_OUTPUTS 1 // Number of outputs to be controlled independently
diff --git a/tasmota/support_features.ino b/tasmota/support_features.ino
index c2e6535c7..b1ac73281 100644
--- a/tasmota/support_features.ino
+++ b/tasmota/support_features.ino
@@ -806,7 +806,9 @@ void ResponseAppendFeatures(void)
#ifdef USE_IMPROV
feature8 |= 0x04000000; // xdrv_62_improv.ino
#endif
-// feature8 |= 0x08000000;
+#ifdef USE_FLOWMETER
+ feature8 |= 0x08000000; // nsns_96_flowmeter.ino
+#endif
// feature8 |= 0x10000000;
// feature8 |= 0x20000000;
From 732359a885be6261120e3d3f32af4b54c5169a77 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 08:22:46 +0200
Subject: [PATCH 05/52] Refactor ISR
---
tasmota/xsns_96_flowmeter.ino | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index 1923fb6e9..2bfd21845 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -50,18 +50,18 @@ bool flowmeter_valuesread = false;
void IRAM_ATTR FlowMeterIR(uint16_t irq)
{
- uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
- GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
uint32_t time = micros();
- uint32_t i = irq;
+ // uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
+ // GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
+ // uint32_t i = irq;
if (irq < MAX_FLOWMETER) {
- if ((time - flowmeter_last_irq[i]) < (1000000 / FLOWMETER_MIN_FREQ)) {
- flowmeter_period[i] = time - flowmeter_last_irq[i];
+ if ((time - flowmeter_last_irq[irq]) < (1000000 / FLOWMETER_MIN_FREQ)) {
+ flowmeter_period[irq] = time - flowmeter_last_irq[irq];
} else {
- flowmeter_period[i] = 0;
+ flowmeter_period[irq] = 0;
}
flowmeter_valuesread = true;
- flowmeter_last_irq[i] = time;
+ flowmeter_last_irq[irq] = time;
}
}
// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way:
From f192284660d4c42ac32544e2c41c4e4bef0e984c Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 08:23:27 +0200
Subject: [PATCH 06/52] Refactor Sensor cmnd
---
tasmota/xsns_96_flowmeter.ino | 20 ++++++++++----------
1 file changed, 10 insertions(+), 10 deletions(-)
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index 2bfd21845..13df5a0a8 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -142,9 +142,9 @@ void FlowMeterShow(bool json)
* Supported commands for Sensor96:
*
* Sensor96 - Show current settings
+ * Sensor96 0 0|1 - Show flow value in l/min (0) or m³/h (1)
* Sensor96 1 - Set sensor 1 factor (x 1000) - to set to 0.2 enter 'Sensor96 1 200'
* Sensor96 2 - Set sensor 2 factor (x 1000)
- * Sensor96 9 0|1 - Show flow value in l/min (0) or m³/h (1)
*
* Flowmeter calibration:
* - get the current displayed flow rate (D)
@@ -175,21 +175,21 @@ bool FlowMeterCommand(void) {
}
switch (XdrvMailbox.payload) {
- case 1: // Calibration value
- case 2: // Calibration value
- if (any_value) {
- Settings->flowmeter_calibration[XdrvMailbox.payload - 1] = value;
- ResponseCmndNumber(value);
- show_parms = false;
- }
- break;
- case 9: // Unit
+ case 0: // Unit
if (any_value) {
Settings->SensorBits1.flowmeter_unit = value & 1;
ResponseCmndNumber(value & 1);
show_parms = false;
}
break;
+ case 1: // Sensor calibration value
+ case 2:
+ if (any_value) {
+ Settings->flowmeter_calibration[XdrvMailbox.payload - 1] = value;
+ ResponseCmndNumber(value);
+ show_parms = false;
+ }
+ break;
}
if (show_parms) {
From 96a36b7bdb85b1e92e48784740653f68b0897ee4 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 08:28:01 +0200
Subject: [PATCH 07/52] Revert "Refactor ISR"
This reverts commit 9033ada3c70c6214770de05c573139c90e08678f.
---
tasmota/xsns_96_flowmeter.ino | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index 13df5a0a8..f30feb7f7 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -50,18 +50,18 @@ bool flowmeter_valuesread = false;
void IRAM_ATTR FlowMeterIR(uint16_t irq)
{
+ uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
+ GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
uint32_t time = micros();
- // uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
- // GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
- // uint32_t i = irq;
+ uint32_t i = irq;
if (irq < MAX_FLOWMETER) {
- if ((time - flowmeter_last_irq[irq]) < (1000000 / FLOWMETER_MIN_FREQ)) {
- flowmeter_period[irq] = time - flowmeter_last_irq[irq];
+ if ((time - flowmeter_last_irq[i]) < (1000000 / FLOWMETER_MIN_FREQ)) {
+ flowmeter_period[i] = time - flowmeter_last_irq[i];
} else {
- flowmeter_period[irq] = 0;
+ flowmeter_period[i] = 0;
}
flowmeter_valuesread = true;
- flowmeter_last_irq[irq] = time;
+ flowmeter_last_irq[i] = time;
}
}
// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way:
From 52757cb8a4ac0ab07c3fb123bc7cf608135bd1df Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 08:32:09 +0200
Subject: [PATCH 08/52] Refactor ISR
---
tasmota/xsns_96_flowmeter.ino | 11 +++++------
1 file changed, 5 insertions(+), 6 deletions(-)
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index f30feb7f7..f57675b6e 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -51,17 +51,16 @@ bool flowmeter_valuesread = false;
void IRAM_ATTR FlowMeterIR(uint16_t irq)
{
uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
- GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
uint32_t time = micros();
- uint32_t i = irq;
+ GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
if (irq < MAX_FLOWMETER) {
- if ((time - flowmeter_last_irq[i]) < (1000000 / FLOWMETER_MIN_FREQ)) {
- flowmeter_period[i] = time - flowmeter_last_irq[i];
+ if ((time - flowmeter_last_irq[irq]) < (1000000 / FLOWMETER_MIN_FREQ)) {
+ flowmeter_period[irq] = time - flowmeter_last_irq[irq];
} else {
- flowmeter_period[i] = 0;
+ flowmeter_period[irq] = 0;
}
flowmeter_valuesread = true;
- flowmeter_last_irq[i] = time;
+ flowmeter_last_irq[irq] = time;
}
}
// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way:
From ff3adb9bf03347a7a40a4350786a50aa48705fb6 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 14:03:05 +0200
Subject: [PATCH 09/52] Add flow rate value source type
---
tasmota/i18n.h | 1 -
tasmota/xsns_96_flowmeter.ino | 60 +++++++++++++++++++++++++----------
2 files changed, 44 insertions(+), 17 deletions(-)
diff --git a/tasmota/i18n.h b/tasmota/i18n.h
index a36001ac9..473bd8b4a 100644
--- a/tasmota/i18n.h
+++ b/tasmota/i18n.h
@@ -225,7 +225,6 @@
#define D_JSON_RESETTABLE_TOTAL_ACTIVE "ResetTotalActive"
#define D_JSON_SIGNALSTRENGTH "SignalStrength"
#define D_JSON_CHIPTEMPERATURE "ChipTemperature"
-#define D_JSON_FLOW_UNIT "FLowUnit"
#define D_RSLT_ENERGY "ENERGY"
#define D_RSLT_HASS_STATE "HASS_STATE"
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowmeter.ino
index f57675b6e..67c755dda 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowmeter.ino
@@ -2,6 +2,7 @@
xsns_96_flowmeter.ino - flowmeter support for Tasmota
Up to two flowmeter YF-DN50 and similary supported
(f = 1 Hz up to 5 kHz)
+ Uses the FreqRes resolution
Copyright (C) 2022 Norbert Richter
@@ -21,17 +22,22 @@
#ifdef USE_FLOWMETER
+// The Arduino standard GPIO routines are not enough,
+// must use some from the Espressif SDK as well
+// extern "C" {
+// #include "gpio.h"
+// }
+
#define XSNS_96 96
#define FLOWMETER_WEIGHT_AVG_SAMPLE 20 // samples
#define FLOWMETER_MIN_FREQ 1 // Hz
-// The Arduino standard GPIO routines are not enough,
-// must use some from the Espressif SDK as well
-extern "C" {
-#include "gpio.h"
-}
-
+#define D_JSON_FLOWMETER_RATE "Rate"
+#define D_JSON_FLOWMETER_VALUE "Value"
+#define D_JSON_FLOWMETER_UNIT "Unit"
+#define D_JSON_FLOWMETER_VALUE_AVG "average"
+#define D_JSON_FLOWMETER_VALUE_RAW "raw"
#ifdef USE_WEBSERVER
const char HTTP_SNS_FLOWMETER[] PROGMEM =
@@ -46,7 +52,7 @@ uint32_t flowmeter_count[MAX_FLOWMETER] = {0};
volatile uint32_t flowmeter_last_irq[MAX_FLOWMETER] = {0};
bool flowmeter_valuesread = false;
-
+bool flowmeter_raw_value = false;
void IRAM_ATTR FlowMeterIR(uint16_t irq)
{
@@ -63,7 +69,7 @@ void IRAM_ATTR FlowMeterIR(uint16_t irq)
flowmeter_last_irq[irq] = time;
}
}
-// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way:
+// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way
void IRAM_ATTR FlowMeter1IR(void)
{
FlowMeterIR(0);
@@ -103,20 +109,27 @@ void FlowMeterInit(void)
void FlowMeterShow(bool json)
{
+ if (json) {
+ ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "\":{\"" D_JSON_FLOWMETER_RATE "\":["));
+ }
+
for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
float flowmeter_rate_avg_float = 0;
if (flowmeter_period[i]) {
flowmeter_rate_avg_float =
- ((Settings->SensorBits1.flowmeter_unit ? (1000000.0 / 1000.0) : (1000000 / 60.0)) / 2.0) / flowmeter_period_avg[i] * (Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] : 1000.0);
+ ((Settings->SensorBits1.flowmeter_unit ? (1000000.0 / 1000.0) : (1000000 / 60.0)) / 2.0)
+ / (flowmeter_raw_value ? flowmeter_period[i] : flowmeter_period_avg[i])
+ * (Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] : 1000.0);
}
if (PinUsed(GPIO_FLOWMETER_IN, i)) {
if (json) {
- ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "-%d\":{\"" D_JSON_FLOWRATE "\":%*_f}"),
- i+1,
+ ResponseAppend_P(PSTR("%s%*_f"),
+ i ? PSTR(",") : PSTR(""),
Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float
);
+
#ifdef USE_WEBSERVER
} else {
WSContentSend_PD(HTTP_SNS_FLOWMETER,
@@ -125,11 +138,15 @@ void FlowMeterShow(bool json)
Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
#endif // USE_WEBSERVER
+
}
}
}
if (json) {
- ResponseAppend_P(PSTR(",\"" D_JSON_FLOW_UNIT "\":\"%s\""),
+ ResponseAppend_P(PSTR("],\"" D_JSON_FLOWMETER_VALUE "\":\"%s\""),
+ flowmeter_raw_value ? PSTR(D_JSON_FLOWMETER_VALUE_RAW) : PSTR(D_JSON_FLOWMETER_VALUE_AVG)
+ );
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOWMETER_UNIT "\":\"%s\"}"),
Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
}
@@ -144,6 +161,7 @@ void FlowMeterShow(bool json)
* Sensor96 0 0|1 - Show flow value in l/min (0) or m³/h (1)
* Sensor96 1 - Set sensor 1 factor (x 1000) - to set to 0.2 enter 'Sensor96 1 200'
* Sensor96 2 - Set sensor 2 factor (x 1000)
+ * Sensor96 9 0|1 - Value mode: Switch between displaying avg(0) / raw(1) readings (not permanently)
*
* Flowmeter calibration:
* - get the current displayed flow rate (D)
@@ -189,15 +207,25 @@ bool FlowMeterCommand(void) {
show_parms = false;
}
break;
+ case 9: // avg/raw values
+ if (any_value) {
+ flowmeter_raw_value = value & 1;
+ ResponseCmndNumber(value & 1);
+ show_parms = false;
+ }
+ break;
}
if (show_parms) {
- Response_P(PSTR("{\"Sensor%d\":{"), XSNS_96);
+ Response_P(PSTR("{\"Sensor%d\":{\"" D_JSON_POWERFACTOR "\":["), XSNS_96);
for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- float flowmeter_factor = Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] / 1000 : 1.0;
- ResponseAppend_P(PSTR("\"" D_JSON_POWERFACTOR "-%d\":%3_f,"), i+1, &flowmeter_factor);
+ float flowmeter_factor = Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] / 1000 : 1;
+ ResponseAppend_P(PSTR("%s%3_f"), i ? PSTR(",") : PSTR(""), &flowmeter_factor);
}
- ResponseAppend_P(PSTR("\"" D_JSON_FLOW_UNIT "\":\"%s\"}}"),
+ ResponseAppend_P(PSTR("],\"" D_JSON_FLOWMETER_VALUE "\":\"%s\""),
+ flowmeter_raw_value ? PSTR(D_JSON_FLOWMETER_VALUE_RAW) : PSTR(D_JSON_FLOWMETER_VALUE_AVG)
+ );
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOWMETER_UNIT "\":\"%s\"}}"),
Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
}
From b1933f7c0e695ebf0f6e6819e717c87b7037e24e Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 16:49:16 +0200
Subject: [PATCH 10/52] Rename flowratemeter
---
BUILDS.md | 2 +-
CHANGELOG.md | 2 +-
tasmota/berry/include/be_gpio_defines.h | 2 +-
tasmota/language/af_AF.h | 7 +-
tasmota/language/bg_BG.h | 7 +-
tasmota/language/cs_CZ.h | 7 +-
tasmota/language/de_DE.h | 7 +-
tasmota/language/el_GR.h | 7 +-
tasmota/language/en_GB.h | 7 +-
tasmota/language/es_ES.h | 7 +-
tasmota/language/fr_FR.h | 7 +-
tasmota/language/fy_NL.h | 7 +-
tasmota/language/he_HE.h | 7 +-
tasmota/language/hu_HU.h | 5 +-
tasmota/language/it_IT.h | 5 +-
tasmota/language/ko_KO.h | 7 +-
tasmota/language/nl_NL.h | 7 +-
tasmota/language/pl_PL.h | 7 +-
tasmota/language/pt_BR.h | 7 +-
tasmota/language/pt_PT.h | 7 +-
tasmota/language/ro_RO.h | 7 +-
tasmota/language/ru_RU.h | 7 +-
tasmota/language/sk_SK.h | 7 +-
tasmota/language/sv_SE.h | 7 +-
tasmota/language/tr_TR.h | 7 +-
tasmota/language/uk_UA.h | 7 +-
tasmota/language/vi_VN.h | 7 +-
tasmota/language/zh_CN.h | 7 +-
tasmota/language/zh_TW.h | 7 +-
tasmota/my_user_config.h | 2 +-
tasmota/settings.h | 4 +-
tasmota/support_features.ino | 4 +-
tasmota/tasmota_template.h | 10 +-
...lowmeter.ino => xsns_96_flowratemeter.ino} | 140 +++++++++---------
tools/lv_gpio/lv_gpio_enum.h | 2 +-
35 files changed, 161 insertions(+), 185 deletions(-)
rename tasmota/{xsns_96_flowmeter.ino => xsns_96_flowratemeter.ino} (52%)
diff --git a/BUILDS.md b/BUILDS.md
index 4b3681d80..c3d70ad51 100644
--- a/BUILDS.md
+++ b/BUILDS.md
@@ -216,7 +216,7 @@ Note: `minimal` variant is not listed as it shouldn't be used outside of the [up
| USE_HRE | - | - / x | - | x | - | - |
| USE_A4988_STEPPER | - | - / - | - | - | - | - |
| USE_NEOPOOL | - | - / - | - | - | - | - |
-| USE_FLOWMETER | - | - / - | - | - | - | - |
+| USE_FLOWRATEMETER | - | - / - | - | - | - | - |
| | | | | | | |
| Feature or Sensor | l | t | k | s | i | d | Remarks
| USE_DISPLAY | - | - / - | - | - | - | x |
diff --git a/CHANGELOG.md b/CHANGELOG.md
index a74756c3a..deb2e5f28 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -11,7 +11,7 @@ All notable changes to this project will be documented in this file.
- Command ``EnergyExportActive`` to (p)reset energy export active for supported devices. Currently ADE7880 only (#13515)
- Sonoff SPM delayed SetPowerOnState (#13447)
- Command ``SetOption139 0/1`` to switch between pressure unit "mmHg" (0) or "inHg" (1) when ``SO24 1`` (#15350)
-- Support for flow meter
+- Support for flowrate meters like YF-DN50 and similary
### Changed
diff --git a/tasmota/berry/include/be_gpio_defines.h b/tasmota/berry/include/be_gpio_defines.h
index b6431945f..6b66aace8 100644
--- a/tasmota/berry/include/be_gpio_defines.h
+++ b/tasmota/berry/include/be_gpio_defines.h
@@ -73,7 +73,7 @@ const be_const_member_t lv_gpio_constants[] = {
{ "ETH_PHY_POWER", (int32_t) GPIO_ETH_PHY_POWER },
{ "EXS_ENABLE", (int32_t) GPIO_EXS_ENABLE },
{ "FALLING", FALLING },
- { "FLOWMETER_SIGNAL", (int32_t) GPIO_FLOWMETER_IN },
+ { "FLOWRATEMETER_SIGNAL", (int32_t) GPIO_FLOWRATEMETER_IN },
{ "FTC532", (int32_t) GPIO_FTC532 },
{ "GPS_RX", (int32_t) GPIO_GPS_RX },
{ "GPS_TX", (int32_t) GPIO_GPS_TX },
diff --git a/tasmota/language/af_AF.h b/tasmota/language/af_AF.h
index 32b04c81c..e421316cc 100644
--- a/tasmota/language/af_AF.h
+++ b/tasmota/language/af_AF.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Wagwoord geverifieer" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fout" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowmeter"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/bg_BG.h b/tasmota/language/bg_BG.h
index f36280949..0e3a49ac0 100644
--- a/tasmota/language/bg_BG.h
+++ b/tasmota/language/bg_BG.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Грешка" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/cs_CZ.h b/tasmota/language/cs_CZ.h
index 32bcea496..69d11e2d8 100644
--- a/tasmota/language/cs_CZ.h
+++ b/tasmota/language/cs_CZ.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/de_DE.h b/tasmota/language/de_DE.h
index c82ea0864..2581479ef 100644
--- a/tasmota/language/de_DE.h
+++ b/tasmota/language/de_DE.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Übereinstimmung" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fehler" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Durchflussmesser"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/el_GR.h b/tasmota/language/el_GR.h
index 2115df377..2586f53fd 100644
--- a/tasmota/language/el_GR.h
+++ b/tasmota/language/el_GR.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/en_GB.h b/tasmota/language/en_GB.h
index 991b51d60..750e68227 100644
--- a/tasmota/language/en_GB.h
+++ b/tasmota/language/en_GB.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/es_ES.h b/tasmota/language/es_ES.h
index e6a61f1af..30fc163f9 100644
--- a/tasmota/language/es_ES.h
+++ b/tasmota/language/es_ES.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Clave Correcta" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/fr_FR.h b/tasmota/language/fr_FR.h
index 56781aaf5..387bb189f 100644
--- a/tasmota/language/fr_FR.h
+++ b/tasmota/language/fr_FR.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Mot-de-passe vérifié" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Erreur" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/fy_NL.h b/tasmota/language/fy_NL.h
index a758a583e..3526a45e0 100644
--- a/tasmota/language/fy_NL.h
+++ b/tasmota/language/fy_NL.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/he_HE.h b/tasmota/language/he_HE.h
index 043401686..f0af2f18b 100644
--- a/tasmota/language/he_HE.h
+++ b/tasmota/language/he_HE.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/hu_HU.h b/tasmota/language/hu_HU.h
index 0eb7d874d..c93e4f809 100644
--- a/tasmota/language/hu_HU.h
+++ b/tasmota/language/hu_HU.h
@@ -1056,9 +1056,8 @@
#define D_FP_PASSVERIFY "Jelszó ellenőrizve" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Hiba" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/it_IT.h b/tasmota/language/it_IT.h
index 7e7ab8830..9197025a6 100644
--- a/tasmota/language/it_IT.h
+++ b/tasmota/language/it_IT.h
@@ -1056,9 +1056,8 @@
#define D_FP_PASSVERIFY "Password verificata" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Errore" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/ko_KO.h b/tasmota/language/ko_KO.h
index de24ea75e..f2182dde3 100644
--- a/tasmota/language/ko_KO.h
+++ b/tasmota/language/ko_KO.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/nl_NL.h b/tasmota/language/nl_NL.h
index d7db56006..5b13fe1eb 100644
--- a/tasmota/language/nl_NL.h
+++ b/tasmota/language/nl_NL.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Wachtwoord herkend" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Fout" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/pl_PL.h b/tasmota/language/pl_PL.h
index 9c6532741..c46c699ee 100644
--- a/tasmota/language/pl_PL.h
+++ b/tasmota/language/pl_PL.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Zweryfikowano poprawnie" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Błąd" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/pt_BR.h b/tasmota/language/pt_BR.h
index ba1b8d5d4..1b05ad513 100644
--- a/tasmota/language/pt_BR.h
+++ b/tasmota/language/pt_BR.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Senha verificada" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Erro" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/pt_PT.h b/tasmota/language/pt_PT.h
index 1ac353e61..c5200a61d 100644
--- a/tasmota/language/pt_PT.h
+++ b/tasmota/language/pt_PT.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/ro_RO.h b/tasmota/language/ro_RO.h
index bc28c0959..095f2a777 100644
--- a/tasmota/language/ro_RO.h
+++ b/tasmota/language/ro_RO.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/ru_RU.h b/tasmota/language/ru_RU.h
index 713dca26f..66b3ded98 100644
--- a/tasmota/language/ru_RU.h
+++ b/tasmota/language/ru_RU.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "А"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/sk_SK.h b/tasmota/language/sk_SK.h
index 17bc2c417..2205db29e 100644
--- a/tasmota/language/sk_SK.h
+++ b/tasmota/language/sk_SK.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/sv_SE.h b/tasmota/language/sv_SE.h
index 28d584288..6727802c7 100644
--- a/tasmota/language/sv_SE.h
+++ b/tasmota/language/sv_SE.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/tr_TR.h b/tasmota/language/tr_TR.h
index e05adff5b..7e0782f36 100644
--- a/tasmota/language/tr_TR.h
+++ b/tasmota/language/tr_TR.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/uk_UA.h b/tasmota/language/uk_UA.h
index 8022a2302..0d9238bc7 100644
--- a/tasmota/language/uk_UA.h
+++ b/tasmota/language/uk_UA.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "А"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/vi_VN.h b/tasmota/language/vi_VN.h
index f04d1196e..98194eae9 100644
--- a/tasmota/language/vi_VN.h
+++ b/tasmota/language/vi_VN.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/zh_CN.h b/tasmota/language/zh_CN.h
index d209c207c..d8631eee4 100644
--- a/tasmota/language/zh_CN.h
+++ b/tasmota/language/zh_CN.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/language/zh_TW.h b/tasmota/language/zh_TW.h
index 3cf448b2e..81616bcfc 100644
--- a/tasmota/language/zh_TW.h
+++ b/tasmota/language/zh_TW.h
@@ -866,7 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
-#define D_SENSOR_FLOWMETER "Flowmeter"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "安培"
@@ -1057,9 +1057,8 @@
#define D_FP_PASSVERIFY "Password verified" // 0x21 Verify the fingerprint passed
#define D_FP_UNKNOWNERROR "Error" // Any other error
-// xsns_96_flowmeter.ino
-#define D_FLOWMETER_NAME "Flowmeter"
-#define D_FLOWMETER_RATE "Rate"
+// xsns_96_flowratemeter.ino
+#define D_FLOWRATEMETER_NAME "Flowrate"
// xsns_83_neopool.ino
#define D_NEOPOOL_MACH_NONE "NeoPool" // Machine names
diff --git a/tasmota/my_user_config.h b/tasmota/my_user_config.h
index 3fdeca42c..47dfef80b 100644
--- a/tasmota/my_user_config.h
+++ b/tasmota/my_user_config.h
@@ -948,7 +948,7 @@
//#define USE_NEOPOOL // Add support for Sugar Valley NeoPool Controller - also known under brands Hidrolife, Aquascenic, Oxilife, Bionet, Hidroniser, UVScenic, Station, Brilix, Bayrol and Hay (+6k flash, +60 mem)
// #define NEOPOOL_MODBUS_ADDRESS 1 // Any modbus address
-//#define FLOWMETER // Add support for water flow meter YF-DN50 and similary (+1k5 code)
+//#define FLOWRATEMETER // Add support for water flow meter YF-DN50 and similary (+1k5 code)
// -- Thermostat control ----------------------------
//#define USE_THERMOSTAT // Add support for Thermostat
diff --git a/tasmota/settings.h b/tasmota/settings.h
index 264b50494..8a302ad55 100644
--- a/tasmota/settings.h
+++ b/tasmota/settings.h
@@ -351,7 +351,7 @@ typedef union {
uint8_t data;
struct {
uint8_t spare0 : 1;
- uint8_t flowmeter_unit : 1; // Sensor96 9,x - unit l/min (0) or m³/h (1)
+ uint8_t flowratemeter_unit : 1; // Sensor96 9,x - unit l/min (0) or m³/h (1)
uint8_t bh1750_2_resolution : 2;
uint8_t bh1750_1_resolution : 2; // Sensor10 1,2,3
uint8_t hx711_json_weight_change : 1; // Sensor34 8,x - Enable JSON message on weight change
@@ -782,7 +782,7 @@ typedef struct {
uint8_t free_f61[23]; // F61 - Decrement if adding new Setting variables just above and below
// Only 32 bit boundary variables below
- uint16_t flowmeter_calibration[2]; // F78
+ uint16_t flowratemeter_calibration[2];// F78
int32_t energy_kWhexport_ph[3]; // F7C
uint32_t eth_ipv4_address[5]; // F88
uint32_t energy_kWhtotal; // F9C
diff --git a/tasmota/support_features.ino b/tasmota/support_features.ino
index b1ac73281..bf3b17011 100644
--- a/tasmota/support_features.ino
+++ b/tasmota/support_features.ino
@@ -806,8 +806,8 @@ void ResponseAppendFeatures(void)
#ifdef USE_IMPROV
feature8 |= 0x04000000; // xdrv_62_improv.ino
#endif
-#ifdef USE_FLOWMETER
- feature8 |= 0x08000000; // nsns_96_flowmeter.ino
+#ifdef USE_FLOWRATEMETER
+ feature8 |= 0x08000000; // xsns_96_flowratemeter.ino
#endif
// feature8 |= 0x10000000;
diff --git a/tasmota/tasmota_template.h b/tasmota/tasmota_template.h
index 0a8f428dc..5c6fa8237 100644
--- a/tasmota/tasmota_template.h
+++ b/tasmota/tasmota_template.h
@@ -187,7 +187,7 @@ enum UserSelectablePins {
GPIO_RESET, // Generic reset
GPIO_MS01, // Sonoff MS01 Moisture Sensor 1wire interface
GPIO_SDIO_CMD, GPIO_SDIO_CLK, GPIO_SDIO_D0, GPIO_SDIO_D1, GPIO_SDIO_D2, GPIO_SDIO_D3, // SD Card SDIO interface, including 1-bit and 4-bit modes
- GPIO_FLOWMETER_IN, // Flow Meter Pin
+ GPIO_FLOWRATEMETER_IN, // Flowrate Meter
GPIO_SENSOR_END };
enum ProgramSelectablePins {
@@ -419,14 +419,14 @@ const char kSensorNames[] PROGMEM =
D_SENSOR_SDIO_D1 "|"
D_SENSOR_SDIO_D2 "|"
D_SENSOR_SDIO_D3 "|"
- D_SENSOR_FLOWMETER "|"
+ D_SENSOR_FLOWRATEMETER "|"
;
const char kSensorNamesFixed[] PROGMEM =
D_SENSOR_USER;
#define MAX_MAX31865S 6
-#define MAX_FLOWMETER 2
+#define MAX_FLOWRATEMETER 2
#define MAX_A4988_MSS 3
#define MAX_WEBCAM_DATA 8
#define MAX_WEBCAM_HSD 3
@@ -977,8 +977,8 @@ const uint16_t kGpioNiceList[] PROGMEM = {
AGPIO(GPIO_CM11_RXD), // CM110x Serial interface
#endif
-#if defined(USE_FLOWMETER)
- AGPIO(GPIO_FLOWMETER_IN) + MAX_FLOWMETER, // Flow meter Pin
+#if defined(USE_FLOWRATEMETER)
+ AGPIO(GPIO_FLOWRATEMETER_IN) + MAX_FLOWRATEMETER, // Flow meter Pin
#endif
/*-------------------------------------------------------------------------------------------*\
diff --git a/tasmota/xsns_96_flowmeter.ino b/tasmota/xsns_96_flowratemeter.ino
similarity index 52%
rename from tasmota/xsns_96_flowmeter.ino
rename to tasmota/xsns_96_flowratemeter.ino
index 67c755dda..b2ff90cab 100644
--- a/tasmota/xsns_96_flowmeter.ino
+++ b/tasmota/xsns_96_flowratemeter.ino
@@ -1,8 +1,8 @@
/*
- xsns_96_flowmeter.ino - flowmeter support for Tasmota
- Up to two flowmeter YF-DN50 and similary supported
- (f = 1 Hz up to 5 kHz)
- Uses the FreqRes resolution
+ xsns_96_flowratemeter.ino - flowratemeter support for Tasmota
+ - up to two flowratemeter YF-DN50 and similary
+ - flow rate frequencies f = 1 Hz up to 5 kHz
+ - uses the FreqRes resolution
Copyright (C) 2022 Norbert Richter
@@ -20,7 +20,7 @@
along with this program. If not, see .
*/
-#ifdef USE_FLOWMETER
+#ifdef USE_FLOWRATEMETER
// The Arduino standard GPIO routines are not enough,
// must use some from the Espressif SDK as well
@@ -30,43 +30,45 @@
#define XSNS_96 96
-#define FLOWMETER_WEIGHT_AVG_SAMPLE 20 // samples
-#define FLOWMETER_MIN_FREQ 1 // Hz
+#define FLOWRATEMETER_WEIGHT_AVG_SAMPLE 20 // samples
+#define FLOWRATEMETER_MIN_FREQ 1 // Hz
-#define D_JSON_FLOWMETER_RATE "Rate"
-#define D_JSON_FLOWMETER_VALUE "Value"
-#define D_JSON_FLOWMETER_UNIT "Unit"
-#define D_JSON_FLOWMETER_VALUE_AVG "average"
-#define D_JSON_FLOWMETER_VALUE_RAW "raw"
+#define D_JSON_FLOWRATEMETER_RATE "Rate"
+#define D_JSON_FLOWRATEMETER_VALUE "Value"
+#define D_JSON_FLOWRATEMETER_UNIT "Unit"
+#define D_JSON_FLOWRATEMETER_VALUE_AVG "average"
+#define D_JSON_FLOWRATEMETER_VALUE_RAW "raw"
#ifdef USE_WEBSERVER
-const char HTTP_SNS_FLOWMETER[] PROGMEM =
- "{s}" D_FLOWMETER_NAME "-%d " D_FLOWMETER_RATE "{m}%*_f %s{e}"
+const char HTTP_SNS_FLOWRATEMETER[] PROGMEM =
+ "{s}" D_FLOWRATEMETER_NAME "-%d{m}%*_f %s{e}"
;
#endif // USE_WEBSERVER
-int32_t flowmeter_period[MAX_FLOWMETER] = {0};
-float flowmeter_period_avg[MAX_FLOWMETER] = {0};
-uint32_t flowmeter_count[MAX_FLOWMETER] = {0};
-volatile uint32_t flowmeter_last_irq[MAX_FLOWMETER] = {0};
+int32_t flowratemeter_period[MAX_FLOWRATEMETER] = {0};
+float flowratemeter_period_avg[MAX_FLOWRATEMETER] = {0};
+uint32_t flowratemeter_count[MAX_FLOWRATEMETER] = {0};
+volatile uint32_t flowratemeter_last_irq[MAX_FLOWRATEMETER] = {0};
-bool flowmeter_valuesread = false;
-bool flowmeter_raw_value = false;
+bool flowratemeter_valuesread = false;
+bool flowratemeter_raw_value = false;
void IRAM_ATTR FlowMeterIR(uint16_t irq)
{
- uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
uint32_t time = micros();
+#if defined(ESP8266)
+ uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
- if (irq < MAX_FLOWMETER) {
- if ((time - flowmeter_last_irq[irq]) < (1000000 / FLOWMETER_MIN_FREQ)) {
- flowmeter_period[irq] = time - flowmeter_last_irq[irq];
+#endif
+ if (irq < MAX_FLOWRATEMETER) {
+ if ((time - flowratemeter_last_irq[irq]) < (1000000 / FLOWRATEMETER_MIN_FREQ)) {
+ flowratemeter_period[irq] = time - flowratemeter_last_irq[irq];
} else {
- flowmeter_period[irq] = 0;
+ flowratemeter_period[irq] = 0;
}
- flowmeter_valuesread = true;
- flowmeter_last_irq[irq] = time;
+ flowratemeter_valuesread = true;
+ flowratemeter_last_irq[irq] = time;
}
}
// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way
@@ -81,61 +83,61 @@ void IRAM_ATTR FlowMeter2IR(void)
void FlowMeterRead(void)
{
- for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- if ((micros() - flowmeter_last_irq[i]) >= (1000000 / FLOWMETER_MIN_FREQ)) {
- flowmeter_period[i] = 0;
- flowmeter_period_avg[i] = 0;
+ for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
+ if ((micros() - flowratemeter_last_irq[i]) >= (1000000 / FLOWRATEMETER_MIN_FREQ)) {
+ flowratemeter_period[i] = 0;
+ flowratemeter_period_avg[i] = 0;
}
// exponentially weighted average
- if (flowmeter_count[i] <= FLOWMETER_WEIGHT_AVG_SAMPLE) {
- flowmeter_count[i]++;
+ if (flowratemeter_count[i] <= FLOWRATEMETER_WEIGHT_AVG_SAMPLE) {
+ flowratemeter_count[i]++;
}
- flowmeter_period_avg[i] -= flowmeter_period_avg[i] / flowmeter_count[i];
- flowmeter_period_avg[i] += float(flowmeter_period[i]) / flowmeter_count[i];
+ flowratemeter_period_avg[i] -= flowratemeter_period_avg[i] / flowratemeter_count[i];
+ flowratemeter_period_avg[i] += float(flowratemeter_period[i]) / flowratemeter_count[i];
}
}
void FlowMeterInit(void)
{
- void (* irq_service[MAX_FLOWMETER])(void)= {FlowMeter1IR, FlowMeter2IR};
+ void (* irq_service[MAX_FLOWRATEMETER])(void)= {FlowMeter1IR, FlowMeter2IR};
- flowmeter_valuesread = false;
- for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- pinMode(Pin(GPIO_FLOWMETER_IN, i), INPUT);
- attachInterrupt(Pin(GPIO_FLOWMETER_IN, i), irq_service[i], RISING);
+ flowratemeter_valuesread = false;
+ for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
+ pinMode(Pin(GPIO_FLOWRATEMETER_IN, i), INPUT);
+ attachInterrupt(Pin(GPIO_FLOWRATEMETER_IN, i), irq_service[i], RISING);
}
}
void FlowMeterShow(bool json)
{
if (json) {
- ResponseAppend_P(PSTR(",\"" D_FLOWMETER_NAME "\":{\"" D_JSON_FLOWMETER_RATE "\":["));
+ ResponseAppend_P(PSTR(",\"" D_FLOWRATEMETER_NAME "\":{\"" D_JSON_FLOWRATEMETER_RATE "\":["));
}
- for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- float flowmeter_rate_avg_float = 0;
+ for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
+ float flowratemeter_rate_avg_float = 0;
- if (flowmeter_period[i]) {
- flowmeter_rate_avg_float =
- ((Settings->SensorBits1.flowmeter_unit ? (1000000.0 / 1000.0) : (1000000 / 60.0)) / 2.0)
- / (flowmeter_raw_value ? flowmeter_period[i] : flowmeter_period_avg[i])
- * (Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] : 1000.0);
+ if (flowratemeter_period[i]) {
+ flowratemeter_rate_avg_float =
+ ((Settings->SensorBits1.flowratemeter_unit ? (1000000.0 / 1000.0) : (1000000 / 60.0)) / 2.0)
+ / (flowratemeter_raw_value ? flowratemeter_period[i] : flowratemeter_period_avg[i])
+ * (Settings->flowratemeter_calibration[i] ? (float)Settings->flowratemeter_calibration[i] : 1000.0);
}
- if (PinUsed(GPIO_FLOWMETER_IN, i)) {
+ if (PinUsed(GPIO_FLOWRATEMETER_IN, i)) {
if (json) {
ResponseAppend_P(PSTR("%s%*_f"),
i ? PSTR(",") : PSTR(""),
- Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float
+ Settings->flag2.frequency_resolution, &flowratemeter_rate_avg_float
);
#ifdef USE_WEBSERVER
} else {
- WSContentSend_PD(HTTP_SNS_FLOWMETER,
+ WSContentSend_PD(HTTP_SNS_FLOWRATEMETER,
i+1,
- Settings->flag2.frequency_resolution, &flowmeter_rate_avg_float,
- Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ Settings->flag2.frequency_resolution, &flowratemeter_rate_avg_float,
+ Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
#endif // USE_WEBSERVER
@@ -143,11 +145,11 @@ void FlowMeterShow(bool json)
}
}
if (json) {
- ResponseAppend_P(PSTR("],\"" D_JSON_FLOWMETER_VALUE "\":\"%s\""),
- flowmeter_raw_value ? PSTR(D_JSON_FLOWMETER_VALUE_RAW) : PSTR(D_JSON_FLOWMETER_VALUE_AVG)
+ ResponseAppend_P(PSTR("],\"" D_JSON_FLOWRATEMETER_VALUE "\":\"%s\""),
+ flowratemeter_raw_value ? PSTR(D_JSON_FLOWRATEMETER_VALUE_RAW) : PSTR(D_JSON_FLOWRATEMETER_VALUE_AVG)
);
- ResponseAppend_P(PSTR(",\"" D_JSON_FLOWMETER_UNIT "\":\"%s\"}"),
- Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOWRATEMETER_UNIT "\":\"%s\"}"),
+ Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
}
}
@@ -194,7 +196,7 @@ bool FlowMeterCommand(void) {
switch (XdrvMailbox.payload) {
case 0: // Unit
if (any_value) {
- Settings->SensorBits1.flowmeter_unit = value & 1;
+ Settings->SensorBits1.flowratemeter_unit = value & 1;
ResponseCmndNumber(value & 1);
show_parms = false;
}
@@ -202,14 +204,14 @@ bool FlowMeterCommand(void) {
case 1: // Sensor calibration value
case 2:
if (any_value) {
- Settings->flowmeter_calibration[XdrvMailbox.payload - 1] = value;
+ Settings->flowratemeter_calibration[XdrvMailbox.payload - 1] = value;
ResponseCmndNumber(value);
show_parms = false;
}
break;
case 9: // avg/raw values
if (any_value) {
- flowmeter_raw_value = value & 1;
+ flowratemeter_raw_value = value & 1;
ResponseCmndNumber(value & 1);
show_parms = false;
}
@@ -218,15 +220,15 @@ bool FlowMeterCommand(void) {
if (show_parms) {
Response_P(PSTR("{\"Sensor%d\":{\"" D_JSON_POWERFACTOR "\":["), XSNS_96);
- for (uint32_t i = 0; i < MAX_FLOWMETER; i++) {
- float flowmeter_factor = Settings->flowmeter_calibration[i] ? (float)Settings->flowmeter_calibration[i] / 1000 : 1;
- ResponseAppend_P(PSTR("%s%3_f"), i ? PSTR(",") : PSTR(""), &flowmeter_factor);
+ for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
+ float flowratemeter_factor = Settings->flowratemeter_calibration[i] ? (float)Settings->flowratemeter_calibration[i] / 1000 : 1;
+ ResponseAppend_P(PSTR("%s%3_f"), i ? PSTR(",") : PSTR(""), &flowratemeter_factor);
}
- ResponseAppend_P(PSTR("],\"" D_JSON_FLOWMETER_VALUE "\":\"%s\""),
- flowmeter_raw_value ? PSTR(D_JSON_FLOWMETER_VALUE_RAW) : PSTR(D_JSON_FLOWMETER_VALUE_AVG)
+ ResponseAppend_P(PSTR("],\"" D_JSON_FLOWRATEMETER_VALUE "\":\"%s\""),
+ flowratemeter_raw_value ? PSTR(D_JSON_FLOWRATEMETER_VALUE_RAW) : PSTR(D_JSON_FLOWRATEMETER_VALUE_AVG)
);
- ResponseAppend_P(PSTR(",\"" D_JSON_FLOWMETER_UNIT "\":\"%s\"}}"),
- Settings->SensorBits1.flowmeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ ResponseAppend_P(PSTR(",\"" D_JSON_FLOWRATEMETER_UNIT "\":\"%s\"}}"),
+ Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
}
@@ -241,7 +243,7 @@ bool Xsns96(uint8_t function)
{
bool result = false;
- if (PinUsed(GPIO_FLOWMETER_IN, GPIO_ANY)) {
+ if (PinUsed(GPIO_FLOWRATEMETER_IN, GPIO_ANY)) {
switch (function) {
case FUNC_INIT:
FlowMeterInit();
@@ -268,4 +270,4 @@ bool Xsns96(uint8_t function)
return result;
}
-#endif // USE_FLOWMETER
+#endif // USE_FLOWRATEMETER
diff --git a/tools/lv_gpio/lv_gpio_enum.h b/tools/lv_gpio/lv_gpio_enum.h
index f6ded405d..cea920168 100644
--- a/tools/lv_gpio/lv_gpio_enum.h
+++ b/tools/lv_gpio/lv_gpio_enum.h
@@ -299,6 +299,6 @@ BL6523_RX = GPIO_BL6523_RX
ADE7880_IRQ = GPIO_ADE7880_IRQ
RESET = GPIO_RESET
-FLOWMETER_SIGNAL = GPIO_FLOWMETER_IN
+FLOWRATEMETER_SIGNAL = GPIO_FLOWRATEMETER_IN
SENSOR_END = GPIO_SENSOR_END
From b5a0c5ca79f50e0fc29daa9e77e4ae73f357564c Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 17:23:34 +0200
Subject: [PATCH 11/52] Fix missing lang definition
---
tasmota/language/hu_HU.h | 1 +
tasmota/language/it_IT.h | 1 +
2 files changed, 2 insertions(+)
diff --git a/tasmota/language/hu_HU.h b/tasmota/language/hu_HU.h
index c93e4f809..fd862bbc8 100644
--- a/tasmota/language/hu_HU.h
+++ b/tasmota/language/hu_HU.h
@@ -866,6 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 SER"
#define D_SENSOR_CM11_TX "CM110x TX"
#define D_SENSOR_CM11_RX "CM110x RX"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
diff --git a/tasmota/language/it_IT.h b/tasmota/language/it_IT.h
index 9197025a6..b19f68536 100644
--- a/tasmota/language/it_IT.h
+++ b/tasmota/language/it_IT.h
@@ -866,6 +866,7 @@
#define D_GPIO_SHIFT595_SER "74x595 - SER"
#define D_SENSOR_CM11_TX "CM110x - TX"
#define D_SENSOR_CM11_RX "CM110x - RX"
+#define D_SENSOR_FLOWRATEMETER "Flowrate"
// Units
#define D_UNIT_AMPERE "A"
From 8d9c945ceee82ad090a23d3aa8f7c95c21090df7 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 17:25:20 +0200
Subject: [PATCH 12/52] Refactor string const
---
tasmota/xsns_96_flowratemeter.ino | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/tasmota/xsns_96_flowratemeter.ino b/tasmota/xsns_96_flowratemeter.ino
index b2ff90cab..010b21885 100644
--- a/tasmota/xsns_96_flowratemeter.ino
+++ b/tasmota/xsns_96_flowratemeter.ino
@@ -149,7 +149,7 @@ void FlowMeterShow(bool json)
flowratemeter_raw_value ? PSTR(D_JSON_FLOWRATEMETER_VALUE_RAW) : PSTR(D_JSON_FLOWRATEMETER_VALUE_AVG)
);
ResponseAppend_P(PSTR(",\"" D_JSON_FLOWRATEMETER_UNIT "\":\"%s\"}"),
- Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ Settings->SensorBits1.flowratemeter_unit ? PSTR(D_UNIT_CUBICMETER_PER_HOUR) : PSTR(D_UNIT_LITER_PER_MINUTE)
);
}
}
@@ -228,7 +228,7 @@ bool FlowMeterCommand(void) {
flowratemeter_raw_value ? PSTR(D_JSON_FLOWRATEMETER_VALUE_RAW) : PSTR(D_JSON_FLOWRATEMETER_VALUE_AVG)
);
ResponseAppend_P(PSTR(",\"" D_JSON_FLOWRATEMETER_UNIT "\":\"%s\"}}"),
- Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
+ Settings->SensorBits1.flowratemeter_unit ? PSTR(D_UNIT_CUBICMETER_PER_HOUR) : PSTR(D_UNIT_LITER_PER_MINUTE)
);
}
From 8857698bc7bddf3063a5d40a85df8b8e09b50372 Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 17:32:52 +0200
Subject: [PATCH 13/52] Update module consumtion
---
tasmota/my_user_config.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tasmota/my_user_config.h b/tasmota/my_user_config.h
index 47dfef80b..a3344e41f 100644
--- a/tasmota/my_user_config.h
+++ b/tasmota/my_user_config.h
@@ -948,7 +948,7 @@
//#define USE_NEOPOOL // Add support for Sugar Valley NeoPool Controller - also known under brands Hidrolife, Aquascenic, Oxilife, Bionet, Hidroniser, UVScenic, Station, Brilix, Bayrol and Hay (+6k flash, +60 mem)
// #define NEOPOOL_MODBUS_ADDRESS 1 // Any modbus address
-//#define FLOWRATEMETER // Add support for water flow meter YF-DN50 and similary (+1k5 code)
+//#define FLOWRATEMETER // Add support for water flow meter YF-DN50 and similary (+1k7 code)
// -- Thermostat control ----------------------------
//#define USE_THERMOSTAT // Add support for Thermostat
From 0ae8bfe2eb603886056c2238b02e2902349884bf Mon Sep 17 00:00:00 2001
From: Norbert Richter
Date: Wed, 27 Apr 2022 17:50:41 +0200
Subject: [PATCH 14/52] Refactor names
---
tasmota/xsns_96_flowratemeter.ino | 49 ++++++++++++++-----------------
1 file changed, 22 insertions(+), 27 deletions(-)
diff --git a/tasmota/xsns_96_flowratemeter.ino b/tasmota/xsns_96_flowratemeter.ino
index 010b21885..1b727dba0 100644
--- a/tasmota/xsns_96_flowratemeter.ino
+++ b/tasmota/xsns_96_flowratemeter.ino
@@ -22,15 +22,11 @@
#ifdef USE_FLOWRATEMETER
-// The Arduino standard GPIO routines are not enough,
-// must use some from the Espressif SDK as well
-// extern "C" {
-// #include "gpio.h"
-// }
-
#define XSNS_96 96
-#define FLOWRATEMETER_WEIGHT_AVG_SAMPLE 20 // samples
+
+
+#define FLOWRATEMETER_WEIGHT_AVG_SAMPLE 20 // number of samples for smooth weigted average
#define FLOWRATEMETER_MIN_FREQ 1 // Hz
#define D_JSON_FLOWRATEMETER_RATE "Rate"
@@ -39,6 +35,8 @@
#define D_JSON_FLOWRATEMETER_VALUE_AVG "average"
#define D_JSON_FLOWRATEMETER_VALUE_RAW "raw"
+
+
#ifdef USE_WEBSERVER
const char HTTP_SNS_FLOWRATEMETER[] PROGMEM =
"{s}" D_FLOWRATEMETER_NAME "-%d{m}%*_f %s{e}"
@@ -54,7 +52,9 @@ volatile uint32_t flowratemeter_last_irq[MAX_FLOWRATEMETER] = {0};
bool flowratemeter_valuesread = false;
bool flowratemeter_raw_value = false;
-void IRAM_ATTR FlowMeterIR(uint16_t irq)
+
+
+void IRAM_ATTR FlowRateMeterIR(uint16_t irq)
{
uint32_t time = micros();
#if defined(ESP8266)
@@ -72,16 +72,16 @@ void IRAM_ATTR FlowMeterIR(uint16_t irq)
}
}
// GPIO_STATUS is always 0 (?), so can only determine the IR source using this way
-void IRAM_ATTR FlowMeter1IR(void)
+void IRAM_ATTR FlowRateMeter1IR(void)
{
- FlowMeterIR(0);
+ FlowRateMeterIR(0);
}
-void IRAM_ATTR FlowMeter2IR(void)
+void IRAM_ATTR FlowRateMeter2IR(void)
{
- FlowMeterIR(1);
+ FlowRateMeterIR(1);
}
-void FlowMeterRead(void)
+void FlowRateMeterRead(void)
{
for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
if ((micros() - flowratemeter_last_irq[i]) >= (1000000 / FLOWRATEMETER_MIN_FREQ)) {
@@ -98,9 +98,9 @@ void FlowMeterRead(void)
}
}
-void FlowMeterInit(void)
+void FlowRateMeterInit(void)
{
- void (* irq_service[MAX_FLOWRATEMETER])(void)= {FlowMeter1IR, FlowMeter2IR};
+ void (* irq_service[MAX_FLOWRATEMETER])(void)= {FlowRateMeter1IR, FlowRateMeter2IR};
flowratemeter_valuesread = false;
for (uint32_t i = 0; i < MAX_FLOWRATEMETER; i++) {
@@ -109,7 +109,7 @@ void FlowMeterInit(void)
}
}
-void FlowMeterShow(bool json)
+void FlowRateMeterShow(bool json)
{
if (json) {
ResponseAppend_P(PSTR(",\"" D_FLOWRATEMETER_NAME "\":{\"" D_JSON_FLOWRATEMETER_RATE "\":["));
@@ -140,7 +140,6 @@ void FlowMeterShow(bool json)
Settings->SensorBits1.flowratemeter_unit ? D_UNIT_CUBICMETER_PER_HOUR : D_UNIT_LITER_PER_MINUTE
);
#endif // USE_WEBSERVER
-
}
}
}
@@ -154,8 +153,6 @@ void FlowMeterShow(bool json)
}
}
-
-
/*********************************************************************************************\
* Supported commands for Sensor96:
*
@@ -179,8 +176,7 @@ void FlowMeterShow(bool json)
* new = M / (c * D) = 83.42 / (1 * 254.39) = 0.328
* Cmd: Sensor96 x 328
\*********************************************************************************************/
-
-bool FlowMeterCommand(void) {
+bool FlowRateMeterCommand(void) {
bool show_parms = true;
char argument[XdrvMailbox.data_len];
@@ -246,25 +242,24 @@ bool Xsns96(uint8_t function)
if (PinUsed(GPIO_FLOWRATEMETER_IN, GPIO_ANY)) {
switch (function) {
case FUNC_INIT:
- FlowMeterInit();
+ FlowRateMeterInit();
break;
case FUNC_EVERY_250_MSECOND:
- FlowMeterRead();
+ FlowRateMeterRead();
break;
case FUNC_COMMAND_SENSOR:
if (XSNS_96 == XdrvMailbox.index) {
- result = FlowMeterCommand();
+ result = FlowRateMeterCommand();
}
break;
case FUNC_JSON_APPEND:
- FlowMeterShow(true);
+ FlowRateMeterShow(true);
break;
#ifdef USE_WEBSERVER
case FUNC_WEB_SENSOR:
- FlowMeterShow(false);
+ FlowRateMeterShow(false);
break;
#endif // USE_WEBSERVER
-
}
}
return result;
From 7acead02f202a985e6154cd8294829c4e49c2d15 Mon Sep 17 00:00:00 2001
From: Jason2866 <24528715+Jason2866@users.noreply.github.com>
Date: Wed, 27 Apr 2022 17:55:14 +0200
Subject: [PATCH 15/52] ArduinoIDE removed
---
README.md | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/README.md b/README.md
index aad266191..59d85d472 100644
--- a/README.md
+++ b/README.md
@@ -1,7 +1,7 @@

Alternative firmware for [ESP8266](https://en.wikipedia.org/wiki/ESP8266) and [ESP32](https://en.wikipedia.org/wiki/ESP32) based devices with **easy configuration using webUI, OTA updates, automation using timers or rules, expandability and entirely local control over MQTT, HTTP, Serial or KNX**.
-_Written for PlatformIO with limited support for Arduino IDE._
+_Written for PlatformIO._
[](http://ota.tasmota.com/tasmota/release)
[](https://github.com/arendst/Tasmota/releases/latest)
From 79c171892beef3a04ba85407157e04ddab40a89c Mon Sep 17 00:00:00 2001
From: Stephan Hadinger
Date: Wed, 27 Apr 2022 18:11:34 +0200
Subject: [PATCH 16/52] Berry fix wrong solidification of class name
---
lib/libesp32/berry/src/be_solidifylib.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/lib/libesp32/berry/src/be_solidifylib.c b/lib/libesp32/berry/src/be_solidifylib.c
index aa030e263..c7d614dbe 100644
--- a/lib/libesp32/berry/src/be_solidifylib.c
+++ b/lib/libesp32/berry/src/be_solidifylib.c
@@ -511,7 +511,7 @@ static void m_solidify_subclass(bvm *vm, bbool str_literal, bclass *cl, int buil
size_t id_len = toidentifier_length(class_name);
char id_buf[id_len];
toidentifier(id_buf, class_name);
- logfmt(" &be_const_str_%s,\n", id_buf);
+ logfmt(" (bstring*) &be_const_str_%s\n", id_buf);
} else {
size_t id_len = toliteral_length(class_name);
char id_buf[id_len];
From d3e55ad43e70043120830ca1d245365ce55f0782 Mon Sep 17 00:00:00 2001
From: Stephan Hadinger
Date: Wed, 27 Apr 2022 18:16:15 +0200
Subject: [PATCH 17/52] Berry solidification of the partition core engine
---
lib/libesp32/berry/default/be_modtab.c | 2 +
lib/libesp32/berry/generate/be_const_strtab.h | 62 +
.../berry/generate/be_const_strtab_def.h | 2417 +++++++++--------
.../berry_tasmota/src/be_partition_module.c | 2085 ++++++++++++++
.../src/embedded/partition_embedded.be | 567 ++++
5 files changed, 3971 insertions(+), 1162 deletions(-)
create mode 100644 lib/libesp32/berry_tasmota/src/be_partition_module.c
create mode 100644 lib/libesp32/berry_tasmota/src/embedded/partition_embedded.be
diff --git a/lib/libesp32/berry/default/be_modtab.c b/lib/libesp32/berry/default/be_modtab.c
index 000e36881..3c8560ce8 100644
--- a/lib/libesp32/berry/default/be_modtab.c
+++ b/lib/libesp32/berry/default/be_modtab.c
@@ -46,6 +46,7 @@ be_extern_native_module(hue_ntv);
be_extern_native_module(hue_bridge);
be_extern_native_module(uuid);
be_extern_native_module(animate);
+be_extern_native_module(partition);
#ifdef USE_LVGL
be_extern_native_module(lv);
be_extern_native_module(lv_extra);
@@ -146,6 +147,7 @@ BERRY_LOCAL const bntvmodule* const be_module_table[] = {
&be_native_module(webserver),
#endif // USE_WEBSERVER
&be_native_module(flash),
+ &be_native_module(partition),
/* user-defined modules register end */
NULL /* do not remove */
diff --git a/lib/libesp32/berry/generate/be_const_strtab.h b/lib/libesp32/berry/generate/be_const_strtab.h
index d4c016e07..332f57979 100644
--- a/lib/libesp32/berry/generate/be_const_strtab.h
+++ b/lib/libesp32/berry/generate/be_const_strtab.h
@@ -1,4 +1,6 @@
extern const bcstring be_const_str_;
+extern const bcstring be_const_str_00;
+extern const bcstring be_const_str_AA50;
extern const bcstring be_const_str_AES_GCM;
extern const bcstring be_const_str_ALIGN_BOTTOM_MID;
extern const bcstring be_const_str_ALIGN_LEFT_MID;
@@ -16,6 +18,7 @@ extern const bcstring be_const_str_Auto_X2Dconfiguration;
extern const bcstring be_const_str_BECDFE;
extern const bcstring be_const_str_BLE;
extern const bcstring be_const_str_BRY_X3A_X20ERROR_X2C_X20bad_X20json_X3A_X20;
+extern const bcstring be_const_str_BRY_X3A_X20Exception_X3E_X20_X27;
extern const bcstring be_const_str_BRY_X3A_X20Exception_X3E_X20_X27_X25s_X27_X20_X2D_X20_X25s;
extern const bcstring be_const_str_BRY_X3A_X20argument_X20must_X20be_X20a_X20function;
extern const bcstring be_const_str_BRY_X3A_X20bytecode_X20has_X20wrong_X20version_X20_X27_X25s_X27_X20_X28_X25i_X29;
@@ -50,12 +53,14 @@ extern const bcstring be_const_str_COLOR_BLACK;
extern const bcstring be_const_str_COLOR_WHITE;
extern const bcstring be_const_str_CT;
extern const bcstring be_const_str_DIMMER;
+extern const bcstring be_const_str_EBEBFFFFFFFFFFFFFFFFFFFFFFFFFFFF;
extern const bcstring be_const_str_EC_C25519;
extern const bcstring be_const_str_EVENT_DELETE;
extern const bcstring be_const_str_EVENT_DRAW_MAIN;
extern const bcstring be_const_str_EVENT_DRAW_PART_BEGIN;
extern const bcstring be_const_str_EVENT_DRAW_PART_END;
extern const bcstring be_const_str_EXTERNAL_I2S;
+extern const bcstring be_const_str_FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF;
extern const bcstring be_const_str_False;
extern const bcstring be_const_str_GET;
extern const bcstring be_const_str_HTTP_GET;
@@ -64,17 +69,22 @@ extern const bcstring be_const_str_I2C_Driver;
extern const bcstring be_const_str_I2C_X3A;
extern const bcstring be_const_str_INTERNAL_DAC;
extern const bcstring be_const_str_INTERNAL_PDM;
+extern const bcstring be_const_str_Invalid_X20ota_X20partition_X20number;
extern const bcstring be_const_str_LVG_X3A_X20call_X20to_X20unsupported_X20callback;
extern const bcstring be_const_str_Leds;
extern const bcstring be_const_str_MAX_RMT;
extern const bcstring be_const_str_MD5;
extern const bcstring be_const_str_MI32;
+extern const bcstring be_const_str_No_X20SPIFFS_X20partition_X20found;
extern const bcstring be_const_str_None;
extern const bcstring be_const_str_OPTION_A;
extern const bcstring be_const_str_OneWire;
extern const bcstring be_const_str_PART_MAIN;
extern const bcstring be_const_str_POST;
extern const bcstring be_const_str_Parameter_X20error;
+extern const bcstring be_const_str_Partition;
+extern const bcstring be_const_str_Partition_info;
+extern const bcstring be_const_str_Partition_otadata;
extern const bcstring be_const_str_RELAY;
extern const bcstring be_const_str_RES_OK;
extern const bcstring be_const_str_RGB;
@@ -111,6 +121,7 @@ extern const bcstring be_const_str_TAP_X3A_X20Loaded_X20Tasmota_X20App_X20_X27_X
extern const bcstring be_const_str_TASMOTA;
extern const bcstring be_const_str_Tasmota;
extern const bcstring be_const_str_Tele;
+extern const bcstring be_const_str_Too_X20many_X20partiition_X20slots;
extern const bcstring be_const_str_Trigger;
extern const bcstring be_const_str_True;
extern const bcstring be_const_str_Unknown;
@@ -120,7 +131,10 @@ extern const bcstring be_const_str_WS2812_GRB;
extern const bcstring be_const_str_Wire;
extern const bcstring be_const_str__;
extern const bcstring be_const_str__X0A;
+extern const bcstring be_const_str__X0A_X29_X3E;
extern const bcstring be_const_str__X20;
+extern const bcstring be_const_str__X20_X20;
+extern const bcstring be_const_str__X20_X28;
extern const bcstring be_const_str__X21_X3D;
extern const bcstring be_const_str__X21_X3D_X3D;
extern const bcstring be_const_str__X22;
@@ -138,7 +152,9 @@ extern const bcstring be_const_str__X2508x_X2D_X2504x_X2D_X2504x_X2D_X2504x_X2D_
extern const bcstring be_const_str__X25s_X2Eautoconf;
extern const bcstring be_const_str__X26lt_X3BError_X3A_X20apply_X20new_X20or_X20remove_X26gt_X3B;
extern const bcstring be_const_str__X26lt_X3BNone_X26gt_X3B;
+extern const bcstring be_const_str__X27_X20_X2D_X20;
extern const bcstring be_const_str__X28_X29;
+extern const bcstring be_const_str__X29;
extern const bcstring be_const_str__X2A;
extern const bcstring be_const_str__X2B;
extern const bcstring be_const_str__X2C;
@@ -172,6 +188,9 @@ extern const bcstring be_const_str__X3C_X3D;
extern const bcstring be_const_str__X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E;
extern const bcstring be_const_str__X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E;
extern const bcstring be_const_str__X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E;
+extern const bcstring be_const_str__X3Cinstance_X3A_X20Partition_X28_X5B_X0A;
+extern const bcstring be_const_str__X3Cinstance_X3A_X20Partition_info_X28_X25d_X25s_X2C_X25d_X25s_X2C0x_X2508X_X2C0x_X2508X_X2C_X27_X25s_X27_X2C0x_X25X_X29_X3E;
+extern const bcstring be_const_str__X3Cinstance_X3A_X20Partition_otadata_X28ota_active_X3A_X25d_X2C_X20ota_seq_X3D_X5B_X25d_X2C_X25d_X5D_X2C_X20ota_max_X3D_X25d_X29_X3E;
extern const bcstring be_const_str__X3Cinstance_X3A_X20_X25s_X28_X25s_X2C_X20_X25s_X2C_X20_X25s_X29;
extern const bcstring be_const_str__X3Clabel_X3EChoose_X20a_X20device_X20configuration_X3A_X3C_X2Flabel_X3E_X3Cbr_X3E;
extern const bcstring be_const_str__X3Clambda_X3E;
@@ -195,6 +214,7 @@ extern const bcstring be_const_str__X3E_X3D;
extern const bcstring be_const_str__X3F;
extern const bcstring be_const_str__X5B;
extern const bcstring be_const_str__X5D;
+extern const bcstring be_const_str__X5D_X2C_X0A_X20_X20;
extern const bcstring be_const_str__X7B;
extern const bcstring be_const_str__X7B_X7D;
extern const bcstring be_const_str__X7Bs_X7DBatt_X20Current_X7Bm_X7D_X25_X2E1f_X20mA_X7Be_X7D;
@@ -240,10 +260,12 @@ extern const bcstring be_const_str__settings_ptr;
extern const bcstring be_const_str__splash;
extern const bcstring be_const_str__t;
extern const bcstring be_const_str__timers;
+extern const bcstring be_const_str__validate;
extern const bcstring be_const_str__write;
extern const bcstring be_const_str_a;
extern const bcstring be_const_str_abs;
extern const bcstring be_const_str_acos;
+extern const bcstring be_const_str_active_otadata;
extern const bcstring be_const_str_add;
extern const bcstring be_const_str_add_anim;
extern const bcstring be_const_str_add_cb_event_closure;
@@ -264,6 +286,7 @@ extern const bcstring be_const_str_allocated;
extern const bcstring be_const_str_alternate;
extern const bcstring be_const_str_animate;
extern const bcstring be_const_str_animators;
+extern const bcstring be_const_str_app;
extern const bcstring be_const_str_arc_dsc;
extern const bcstring be_const_str_arch;
extern const bcstring be_const_str_area;
@@ -353,11 +376,15 @@ extern const bcstring be_const_str_content_stop;
extern const bcstring be_const_str_continue;
extern const bcstring be_const_str_coord_arr;
extern const bcstring be_const_str_copy;
+extern const bcstring be_const_str_coredump;
extern const bcstring be_const_str_cos;
extern const bcstring be_const_str_cosh;
extern const bcstring be_const_str_couldn_X27t_X20not_X20initialize_X20noepixelbus;
extern const bcstring be_const_str_count;
extern const bcstring be_const_str_counters;
+extern const bcstring be_const_str_crc32_ota_seq;
+extern const bcstring be_const_str_crc32_table;
+extern const bcstring be_const_str_crc32_update;
extern const bcstring be_const_str_create_custom_widget;
extern const bcstring be_const_str_create_matrix;
extern const bcstring be_const_str_create_segment;
@@ -366,6 +393,7 @@ extern const bcstring be_const_str_ctor;
extern const bcstring be_const_str_ctypes_bytes;
extern const bcstring be_const_str_ctypes_bytes_dyn;
extern const bcstring be_const_str_dac_voltage;
+extern const bcstring be_const_str_data;
extern const bcstring be_const_str_day;
extern const bcstring be_const_str_debug;
extern const bcstring be_const_str_decode;
@@ -403,6 +431,7 @@ extern const bcstring be_const_str_driver_name;
extern const bcstring be_const_str_dump;
extern const bcstring be_const_str_duration;
extern const bcstring be_const_str_editable;
+extern const bcstring be_const_str_efuse_em;
extern const bcstring be_const_str_elements_X20must_X20be_X20a_X20lv_point;
extern const bcstring be_const_str_elif;
extern const bcstring be_const_str_else;
@@ -413,6 +442,7 @@ extern const bcstring be_const_str_energy_struct;
extern const bcstring be_const_str_engine;
extern const bcstring be_const_str_erase;
extern const bcstring be_const_str_escape;
+extern const bcstring be_const_str_esphttpd;
extern const bcstring be_const_str_eth;
extern const bcstring be_const_str_event;
extern const bcstring be_const_str_event_cb;
@@ -428,9 +458,11 @@ extern const bcstring be_const_str_exec_tele;
extern const bcstring be_const_str_exists;
extern const bcstring be_const_str_exp;
extern const bcstring be_const_str_f;
+extern const bcstring be_const_str_factory;
extern const bcstring be_const_str_false;
extern const bcstring be_const_str_fast_loop;
extern const bcstring be_const_str_fast_loop_enabled;
+extern const bcstring be_const_str_fat;
extern const bcstring be_const_str_file;
extern const bcstring be_const_str_file_X20extension_X20is_X20not_X20_X27_X2Ebe_X27_X20or_X20_X27_X2Ebec_X27;
extern const bcstring be_const_str_files;
@@ -438,6 +470,8 @@ extern const bcstring be_const_str_find;
extern const bcstring be_const_str_find_key_i;
extern const bcstring be_const_str_find_op;
extern const bcstring be_const_str_finish;
+extern const bcstring be_const_str_flags;
+extern const bcstring be_const_str_flash;
extern const bcstring be_const_str_floor;
extern const bcstring be_const_str_flush;
extern const bcstring be_const_str_font_embedded;
@@ -460,6 +494,7 @@ extern const bcstring be_const_str_gc;
extern const bcstring be_const_str_gen_cb;
extern const bcstring be_const_str_get;
extern const bcstring be_const_str_get_MAC;
+extern const bcstring be_const_str_get_active;
extern const bcstring be_const_str_get_alternate;
extern const bcstring be_const_str_get_aps_voltage;
extern const bcstring be_const_str_get_bat_charge_current;
@@ -476,12 +511,14 @@ extern const bcstring be_const_str_get_event_cb;
extern const bcstring be_const_str_get_free_heap;
extern const bcstring be_const_str_get_height;
extern const bcstring be_const_str_get_hor_res;
+extern const bcstring be_const_str_get_image_size;
extern const bcstring be_const_str_get_input_power_status;
extern const bcstring be_const_str_get_light;
extern const bcstring be_const_str_get_log;
extern const bcstring be_const_str_get_name;
extern const bcstring be_const_str_get_object_from_ptr;
extern const bcstring be_const_str_get_option;
+extern const bcstring be_const_str_get_ota_slot;
extern const bcstring be_const_str_get_percentage;
extern const bcstring be_const_str_get_pixel_color;
extern const bcstring be_const_str_get_power;
@@ -540,12 +577,16 @@ extern const bcstring be_const_str_int64;
extern const bcstring be_const_str_internal_error;
extern const bcstring be_const_str_introspect;
extern const bcstring be_const_str_invalid_X20GPIO_X20number;
+extern const bcstring be_const_str_invalid_X20magic_X20number_X20_X2502X;
extern const bcstring be_const_str_invalidate;
+extern const bcstring be_const_str_invalidate_spiffs;
extern const bcstring be_const_str_io_error;
extern const bcstring be_const_str_ip;
extern const bcstring be_const_str_is_dirty;
extern const bcstring be_const_str_is_first_time;
+extern const bcstring be_const_str_is_ota;
extern const bcstring be_const_str_is_running;
+extern const bcstring be_const_str_is_spiffs;
extern const bcstring be_const_str_isinstance;
extern const bcstring be_const_str_ismethod;
extern const bcstring be_const_str_isnan;
@@ -575,6 +616,7 @@ extern const bcstring be_const_str_list_handlers;
extern const bcstring be_const_str_listdir;
extern const bcstring be_const_str_load;
extern const bcstring be_const_str_load_freetype_font;
+extern const bcstring be_const_str_load_otadata;
extern const bcstring be_const_str_load_templates;
extern const bcstring be_const_str_local;
extern const bcstring be_const_str_log;
@@ -610,6 +652,8 @@ extern const bcstring be_const_str_manuf;
extern const bcstring be_const_str_map;
extern const bcstring be_const_str_math;
extern const bcstring be_const_str_matrix;
+extern const bcstring be_const_str_maxota;
+extern const bcstring be_const_str_md5;
extern const bcstring be_const_str_member;
extern const bcstring be_const_str_members;
extern const bcstring be_const_str_memory;
@@ -631,6 +675,8 @@ extern const bcstring be_const_str_no_X20more_X20RMT_X20channel_X20available;
extern const bcstring be_const_str_now;
extern const bcstring be_const_str_null_cb;
extern const bcstring be_const_str_number;
+extern const bcstring be_const_str_nvs;
+extern const bcstring be_const_str_nvskeys;
extern const bcstring be_const_str_o;
extern const bcstring be_const_str_obj;
extern const bcstring be_const_str_obj_class_create_obj;
@@ -641,12 +687,17 @@ extern const bcstring be_const_str_on;
extern const bcstring be_const_str_onsubmit_X3D_X27return_X20confirm_X28_X22This_X20will_X20cause_X20a_X20restart_X2E_X22_X29_X3B_X27_X3E;
extern const bcstring be_const_str_onsubmit_X3D_X27return_X20confirm_X28_X22This_X20will_X20change_X20the_X20current_X20configuration_X20and_X20cause_X20a_X20restart_X2E_X22_X29_X3B_X27_X3E;
extern const bcstring be_const_str_open;
+extern const bcstring be_const_str_ota;
+extern const bcstring be_const_str_ota_max;
+extern const bcstring be_const_str_otadata;
extern const bcstring be_const_str_out_X20of_X20range;
extern const bcstring be_const_str_p1;
extern const bcstring be_const_str_p2;
extern const bcstring be_const_str_page_autoconf_ctl;
extern const bcstring be_const_str_page_autoconf_mgr;
extern const bcstring be_const_str_param;
+extern const bcstring be_const_str_parse;
+extern const bcstring be_const_str_partition;
extern const bcstring be_const_str_path;
extern const bcstring be_const_str_pc;
extern const bcstring be_const_str_pc_abs;
@@ -655,6 +706,7 @@ extern const bcstring be_const_str_pct;
extern const bcstring be_const_str_percentage;
extern const bcstring be_const_str_persist;
extern const bcstring be_const_str_persist_X2E_p_X20is_X20not_X20a_X20map;
+extern const bcstring be_const_str_phy;
extern const bcstring be_const_str_pi;
extern const bcstring be_const_str_pin;
extern const bcstring be_const_str_pin_mode;
@@ -683,6 +735,7 @@ extern const bcstring be_const_str_rad;
extern const bcstring be_const_str_raise;
extern const bcstring be_const_str_rand;
extern const bcstring be_const_str_range;
+extern const bcstring be_const_str_raw;
extern const bcstring be_const_str_read;
extern const bcstring be_const_str_read12;
extern const bcstring be_const_str_read13;
@@ -710,6 +763,7 @@ extern const bcstring be_const_str_remove_driver;
extern const bcstring be_const_str_remove_light;
extern const bcstring be_const_str_remove_rule;
extern const bcstring be_const_str_remove_timer;
+extern const bcstring be_const_str_remove_trailing_zeroes;
extern const bcstring be_const_str_reset;
extern const bcstring be_const_str_reset_search;
extern const bcstring be_const_str_resize;
@@ -748,9 +802,12 @@ extern const bcstring be_const_str_seg7_font;
extern const bcstring be_const_str_select;
extern const bcstring be_const_str_send;
extern const bcstring be_const_str_send_multicast;
+extern const bcstring be_const_str_seq0;
+extern const bcstring be_const_str_seq1;
extern const bcstring be_const_str_serial;
extern const bcstring be_const_str_set;
extern const bcstring be_const_str_set_MAC;
+extern const bcstring be_const_str_set_active;
extern const bcstring be_const_str_set_align;
extern const bcstring be_const_str_set_alternate;
extern const bcstring be_const_str_set_auth;
@@ -776,6 +833,7 @@ extern const bcstring be_const_str_set_light;
extern const bcstring be_const_str_set_matrix_pixel_color;
extern const bcstring be_const_str_set_mode_ct;
extern const bcstring be_const_str_set_mode_rgb;
+extern const bcstring be_const_str_set_ota_max;
extern const bcstring be_const_str_set_percentage;
extern const bcstring be_const_str_set_pixel_color;
extern const bcstring be_const_str_set_power;
@@ -824,7 +882,9 @@ extern const bcstring be_const_str_sin;
extern const bcstring be_const_str_sinh;
extern const bcstring be_const_str_size;
extern const bcstring be_const_str_skip;
+extern const bcstring be_const_str_slots;
extern const bcstring be_const_str_solidified;
+extern const bcstring be_const_str_spiffs;
extern const bcstring be_const_str_splash;
extern const bcstring be_const_str_splash_init;
extern const bcstring be_const_str_splash_remove;
@@ -844,6 +904,7 @@ extern const bcstring be_const_str_strip;
extern const bcstring be_const_str_strptime;
extern const bcstring be_const_str_style_prop_arr;
extern const bcstring be_const_str_subscribe;
+extern const bcstring be_const_str_subtype;
extern const bcstring be_const_str_success;
extern const bcstring be_const_str_super;
extern const bcstring be_const_str_sys;
@@ -858,6 +919,7 @@ extern const bcstring be_const_str_tasmota_X2Eset_light_X28_X29_X20is_X20depreca
extern const bcstring be_const_str_tasmota_log_reader;
extern const bcstring be_const_str_tcpclient;
extern const bcstring be_const_str_tele;
+extern const bcstring be_const_str_test;
extern const bcstring be_const_str_the_X20second_X20argument_X20is_X20not_X20a_X20function;
extern const bcstring be_const_str_time_dump;
extern const bcstring be_const_str_time_reached;
diff --git a/lib/libesp32/berry/generate/be_const_strtab_def.h b/lib/libesp32/berry/generate/be_const_strtab_def.h
index 23aceb41b..5d31477c0 100644
--- a/lib/libesp32/berry/generate/be_const_strtab_def.h
+++ b/lib/libesp32/berry/generate/be_const_strtab_def.h
@@ -1,779 +1,837 @@
-be_define_const_str(, "", 2166136261u, 0, 0, &be_const_str_driver_name);
-be_define_const_str(_X0A, "\n", 252472541u, 0, 1, &be_const_str_autoexec);
-be_define_const_str(_X20, " ", 621580159u, 0, 1, &be_const_str_stop);
-be_define_const_str(_X21_X3D, "!=", 2428715011u, 0, 2, &be_const_str_editable);
-be_define_const_str(_X21_X3D_X3D, "!==", 559817114u, 0, 3, &be_const_str_cb_obj);
-be_define_const_str(_X22, "\"", 655135397u, 0, 1, &be_const_str_RGBW);
-be_define_const_str(_X22_X3A, "\":", 399167565u, 0, 2, &be_const_str__X2F_X2Eautoconf);
-be_define_const_str(_X23, "#", 638357778u, 0, 1, &be_const_str_write);
-be_define_const_str(_X23autoexec_X2Ebat, "#autoexec.bat", 3382890497u, 0, 13, &be_const_str_SERIAL_5O1);
-be_define_const_str(_X23autoexec_X2Ebe, "#autoexec.be", 1181757091u, 0, 12, &be_const_str_font_embedded);
-be_define_const_str(_X23display_X2Eini, "#display.ini", 182218220u, 0, 12, &be_const_str_INTERNAL_PDM);
-be_define_const_str(_X23init_X2Ebat, "#init.bat", 3297595077u, 0, 9, &be_const_str_MD5);
-be_define_const_str(_X23preinit_X2Ebe, "#preinit.be", 687035716u, 0, 11, &be_const_str_False);
-be_define_const_str(_X25, "%", 537692064u, 0, 1, &be_const_str_classname);
-be_define_const_str(_X2502d_X25s_X2502d, "%02d%s%02d", 1587999717u, 0, 10, &be_const_str_EXTERNAL_I2S);
-be_define_const_str(_X2504d_X2D_X2502d_X2D_X2502dT_X2502d_X3A_X2502d_X3A_X2502d, "%04d-%02d-%02dT%02d:%02d:%02d", 3425528601u, 0, 29, &be_const_str__X2A);
-be_define_const_str(_X2508x_X2D_X2504x_X2D_X2504x_X2D_X2504x_X2D_X2504x_X2508x, "%08x-%04x-%04x-%04x-%04x%08x", 1670063141u, 0, 28, &be_const_str_Auto_X2Dconfiguration);
-be_define_const_str(_X25s_X2Eautoconf, "%s.autoconf", 3560383524u, 0, 11, &be_const_str_pc);
-be_define_const_str(_X26lt_X3BError_X3A_X20apply_X20new_X20or_X20remove_X26gt_X3B, "<Error: apply new or remove>", 2855507949u, 0, 34, &be_const_str_h);
-be_define_const_str(_X26lt_X3BNone_X26gt_X3B, "<None>", 2602165498u, 0, 12, &be_const_str_send_multicast);
-be_define_const_str(_X28_X29, "()", 685372826u, 0, 2, &be_const_str_available);
-be_define_const_str(_X2A, "*", 789356349u, 0, 1, &be_const_str__settings_def);
-be_define_const_str(_X2B, "+", 772578730u, 0, 1, &be_const_str_id_X20must_X20be_X20of_X20type_X20_X27int_X27);
-be_define_const_str(_X2C, ",", 688690635u, 0, 1, NULL);
-be_define_const_str(_X2C_X22AXP192_X22_X3A_X7B_X22VBusVoltage_X22_X3A_X25_X2E3f_X2C_X22VBusCurrent_X22_X3A_X25_X2E1f_X2C_X22BattVoltage_X22_X3A_X25_X2E3f_X2C_X22BattCurrent_X22_X3A_X25_X2E1f_X2C_X22Temperature_X22_X3A_X25_X2E1f_X7D, ",\"AXP192\":{\"VBusVoltage\":%.3f,\"VBusCurrent\":%.1f,\"BattVoltage\":%.3f,\"BattCurrent\":%.1f,\"Temperature\":%.1f}", 2598755376u, 0, 106, &be_const_str_isnan);
-be_define_const_str(_X2D, "-", 671913016u, 0, 1, NULL);
-be_define_const_str(_X2D_X2A, "-*", 499980374u, 0, 2, &be_const_str_BECDFE);
-be_define_const_str(_X2D_X2D_X3A_X2D_X2D, "--:--", 1370615441u, 0, 5, &be_const_str_add_driver);
-be_define_const_str(_X2E, ".", 722245873u, 0, 1, &be_const_str_load_templates);
-be_define_const_str(_X2E_X2E, "..", 2748622605u, 0, 2, NULL);
-be_define_const_str(_X2Eautoconf, ".autoconf", 2524679088u, 0, 9, &be_const_str_animate);
-be_define_const_str(_X2Ebe, ".be", 1325797348u, 0, 3, &be_const_str_RGB);
-be_define_const_str(_X2Ebec, ".bec", 3985273221u, 0, 4, &be_const_str_get_input_power_status);
-be_define_const_str(_X2Elen, ".len", 850842136u, 0, 4, &be_const_str_begin);
-be_define_const_str(_X2Ep, ".p", 1171526419u, 0, 2, &be_const_str_file_X20extension_X20is_X20not_X20_X27_X2Ebe_X27_X20or_X20_X27_X2Ebec_X27);
-be_define_const_str(_X2Ep1, ".p1", 249175686u, 0, 3, &be_const_str_AES_GCM);
-be_define_const_str(_X2Ep2, ".p2", 232398067u, 0, 3, &be_const_str_get_bri);
-be_define_const_str(_X2Esize, ".size", 1965188224u, 0, 5, &be_const_str__X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E);
-be_define_const_str(_X2Etapp, ".tapp", 1363391594u, 0, 5, &be_const_str_assign_rmt);
-be_define_const_str(_X2Ew, ".w", 1255414514u, 0, 2, &be_const_str_load_freetype_font);
-be_define_const_str(_X2F, "/", 705468254u, 0, 1, &be_const_str_class_init_obj);
-be_define_const_str(_X2F_X2Eautoconf, "/.autoconf", 2212074393u, 0, 10, NULL);
-be_define_const_str(_X2F_X3Frst_X3D, "/?rst=", 580074707u, 0, 6, &be_const_str_every_second);
-be_define_const_str(_X2Fac, "/ac", 3904651978u, 0, 3, &be_const_str_get_alternate);
-be_define_const_str(_X2Flights_X2F, "/lights/", 2370247908u, 0, 8, &be_const_str_arc_dsc);
-be_define_const_str(_X2Fstate_X2F, "/state/", 4226179876u, 0, 7, &be_const_str___lower__);
-be_define_const_str(_X3A, ":", 1057798253u, 0, 1, &be_const_str_EVENT_DELETE);
-be_define_const_str(_X3C, "<", 957132539u, 0, 1, &be_const_str_POST);
-be_define_const_str(_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "
", 3546571739u, 0, 11, &be_const_str_json_fdump_any);
-be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, &be_const_str_loop);
-be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_import);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_chars_in_string);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str_content_send_style);
-be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, &be_const_str_CFG_X3A_X20loaded_X20_X20);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_arch);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "", 3546571739u, 0, 11, &be_const_str_load_templates);
+be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, &be_const_str_check_not_method);
+be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_set_pwm);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_SERIAL_6O1);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str__persist_X2Ejson);
+be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, NULL);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_classof);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "", 3546571739u, 0, 11, &be_const_str_load_templates);
-be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, &be_const_str_check_not_method);
-be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_set_pwm);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_SERIAL_6O1);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str__persist_X2Ejson);
-be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, NULL);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_classof);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "", 3546571739u, 0, 11, &be_const_str__X3Cp_X3ECurrent_X20configuration_X3A_X20_X3C_X2Fp_X3E_X3Cp_X3E_X3Cb_X3E_X25s_X3C_X2Fb_X3E_X3C_X2Fp_X3E);
+be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, NULL);
+be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_SERIAL_5E2);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_couldn_X27t_X20not_X20initialize_X20noepixelbus);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str_json_fdump_list);
+be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, &be_const_str_continue);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_get_power);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "", 3546571739u, 0, 11, &be_const_str__X3Cp_X3ECurrent_X20configuration_X3A_X20_X3C_X2Fp_X3E_X3Cp_X3E_X3Cb_X3E_X25s_X3C_X2Fb_X3E_X3C_X2Fp_X3E);
-be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, NULL);
-be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_SERIAL_5E2);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_couldn_X27t_X20not_X20initialize_X20noepixelbus);
-be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str_json_fdump_list);
-be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, &be_const_str_continue);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_get_power);
-be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "", 3546571739u, 0, 11, NULL);
+be_define_const_str(_X3C_X2Fselect_X3E_X3Cp_X3E_X3C_X2Fp_X3E, "", 1863865923u, 0, 16, &be_const_str_MI32);
+be_define_const_str(_X3C_X3D, "<=", 2499223986u, 0, 2, &be_const_str_power_off);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27reapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3ERe_X2Dapply_X20current_X20configuration_X3C_X2Fbutton_X3E, "", 3147934216u, 0, 82, &be_const_str_AudioFileSource);
+be_define_const_str(_X3Cbutton_X20name_X3D_X27zipapply_X27_X20class_X3D_X27button_X20bgrn_X27_X3EApply_X20configuration_X3C_X2Fbutton_X3E, "", 1205771629u, 0, 72, &be_const_str_PART_MAIN);
+be_define_const_str(_X3Cfieldset_X3E_X3Cstyle_X3E_X2Ebdis_X7Bbackground_X3A_X23888_X3B_X7D_X2Ebdis_X3Ahover_X7Bbackground_X3A_X23888_X3B_X7D_X3C_X2Fstyle_X3E, "", 2052843416u, 0, 25, &be_const_str_subscribe);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dac_X20action_X3D_X27ac_X27_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20method_X3D_X27get_X27_X3E_X3Cbutton_X3EAuto_X2Dconfiguration_X3C_X2Fbutton_X3E_X3C_X2Fform_X3E_X3C_X2Fp_X3E, "", 2058443583u, 0, 110, &be_const_str_consume_silence);
+be_define_const_str(_X3Cp_X3E_X3Cform_X20id_X3Dreapply_X20style_X3D_X27display_X3A_X20block_X3B_X27_X20action_X3D_X27_X2Fac_X27_X20method_X3D_X27post_X27_X20, "