Implement battery drain strategies:
- empty when full - empty at night
This commit is contained in:
parent
32a96bbd06
commit
46ce6ad50f
@ -101,6 +101,7 @@ struct CONFIG_T {
|
||||
|
||||
bool PowerLimiter_Enabled;
|
||||
bool PowerLimiter_SolarPassTroughEnabled;
|
||||
uint8_t PowerLimiter_BatteryDrainStategy;
|
||||
uint32_t PowerLimiter_Interval;
|
||||
char PowerLimiter_MqttTopicPowerMeter1[MQTT_MAX_TOPIC_STRLEN + 1];
|
||||
char PowerLimiter_MqttTopicPowerMeter2[MQTT_MAX_TOPIC_STRLEN + 1];
|
||||
|
||||
@ -13,6 +13,11 @@ typedef enum {
|
||||
STATE_CONSUME_SOLAR_POWER_ONLY,
|
||||
STATE_NORMAL_OPERATION
|
||||
} plStates;
|
||||
|
||||
typedef enum {
|
||||
EMPTY_WHEN_FULL= 0,
|
||||
EMPTY_AT_NIGTH
|
||||
} batDrainStrategy;
|
||||
|
||||
|
||||
class PowerLimiterClass {
|
||||
|
||||
@ -94,6 +94,7 @@
|
||||
|
||||
#define POWERLIMITER_ENABLED false
|
||||
#define POWERLIMITER_SOLAR_PASSTROUGH_ENABLED true
|
||||
#define POWERLIMITER_BATTERY_DRAIN_STRATEGY 0
|
||||
#define POWERLIMITER_INTERVAL 10
|
||||
#define POWERLIMITER_IS_INVERTER_BEHIND_POWER_METER true
|
||||
#define POWERLIMITER_INVERTER_ID 0
|
||||
|
||||
@ -118,6 +118,7 @@ bool ConfigurationClass::write()
|
||||
JsonObject powerlimiter = doc.createNestedObject("powerlimiter");
|
||||
powerlimiter["enabled"] = config.PowerLimiter_Enabled;
|
||||
powerlimiter["solar_passtrough_enabled"] = config.PowerLimiter_SolarPassTroughEnabled;
|
||||
powerlimiter["battery_drain_strategy"] = config.PowerLimiter_BatteryDrainStategy;
|
||||
powerlimiter["interval"] = config.PowerLimiter_Interval;
|
||||
powerlimiter["mqtt_topic_powermeter_1"] = config.PowerLimiter_MqttTopicPowerMeter1;
|
||||
powerlimiter["mqtt_topic_powermeter_2"] = config.PowerLimiter_MqttTopicPowerMeter2;
|
||||
@ -283,6 +284,7 @@ bool ConfigurationClass::read()
|
||||
JsonObject powerlimiter = doc["powerlimiter"];
|
||||
config.PowerLimiter_Enabled = powerlimiter["enabled"] | POWERLIMITER_ENABLED;
|
||||
config.PowerLimiter_SolarPassTroughEnabled = powerlimiter["solar_passtrough_enabled"] | POWERLIMITER_SOLAR_PASSTROUGH_ENABLED;
|
||||
config.PowerLimiter_BatteryDrainStategy = powerlimiter["battery_drain_strategy"] | POWERLIMITER_BATTERY_DRAIN_STRATEGY;
|
||||
config.PowerLimiter_Interval = POWERLIMITER_INTERVAL;
|
||||
strlcpy(config.PowerLimiter_MqttTopicPowerMeter1, powerlimiter["mqtt_topic_powermeter_1"] | "", sizeof(config.PowerLimiter_MqttTopicPowerMeter1));
|
||||
strlcpy(config.PowerLimiter_MqttTopicPowerMeter2, powerlimiter["mqtt_topic_powermeter_2"] | "", sizeof(config.PowerLimiter_MqttTopicPowerMeter2));
|
||||
|
||||
@ -149,7 +149,7 @@ void PowerLimiterClass::loop()
|
||||
int32_t newPowerLimit = calcPowerLimit(inverter, true);
|
||||
if (!inverter->isProducing()
|
||||
|| isStopThresholdReached(inverter)
|
||||
|| newPowerLimit < config.PowerLimiter_LowerPowerLimit) {
|
||||
|| (newPowerLimit < config.PowerLimiter_LowerPowerLimit && config.PowerLimiter_BatteryDrainStategy == EMPTY_WHEN_FULL)) {
|
||||
_plState = STATE_OFF;
|
||||
break;
|
||||
}
|
||||
|
||||
@ -37,6 +37,7 @@ void WebApiPowerLimiterClass::onStatus(AsyncWebServerRequest* request)
|
||||
|
||||
root[F("enabled")] = config.PowerLimiter_Enabled;
|
||||
root[F("solar_passtrough_enabled")] = config.PowerLimiter_SolarPassTroughEnabled;
|
||||
root[F("battery_drain_strategy")] = config.PowerLimiter_BatteryDrainStategy;
|
||||
root[F("mqtt_topic_powermeter_1")] = config.PowerLimiter_MqttTopicPowerMeter1;
|
||||
root[F("mqtt_topic_powermeter_2")] = config.PowerLimiter_MqttTopicPowerMeter2;
|
||||
root[F("mqtt_topic_powermeter_3")] = config.PowerLimiter_MqttTopicPowerMeter3;
|
||||
@ -120,6 +121,7 @@ void WebApiPowerLimiterClass::onAdminPost(AsyncWebServerRequest* request)
|
||||
CONFIG_T& config = Configuration.get();
|
||||
config.PowerLimiter_Enabled = root[F("enabled")].as<bool>();
|
||||
config.PowerLimiter_SolarPassTroughEnabled = root[F("solar_passtrough_enabled")].as<bool>();
|
||||
config.PowerLimiter_BatteryDrainStategy= root[F("battery_drain_strategy")].as<uint8_t>();
|
||||
strlcpy(config.PowerLimiter_MqttTopicPowerMeter1, root[F("mqtt_topic_powermeter_1")].as<String>().c_str(), sizeof(config.PowerLimiter_MqttTopicPowerMeter1));
|
||||
strlcpy(config.PowerLimiter_MqttTopicPowerMeter2, root[F("mqtt_topic_powermeter_2")].as<String>().c_str(), sizeof(config.PowerLimiter_MqttTopicPowerMeter2));
|
||||
strlcpy(config.PowerLimiter_MqttTopicPowerMeter3, root[F("mqtt_topic_powermeter_3")].as<String>().c_str(), sizeof(config.PowerLimiter_MqttTopicPowerMeter3));
|
||||
|
||||
@ -458,6 +458,9 @@
|
||||
"General": "Allgemein",
|
||||
"Enable": "Aktiviert",
|
||||
"EnableSolarPasstrough": "Aktiviere Solar Pass-trough",
|
||||
"BatteryDrainStrategy": "Strategie zur Batterieentleerung",
|
||||
"BatteryDrainWhenFull": "Leeren, wenn voll",
|
||||
"BatteryDrainAtNight": "Leeren zur Nacht",
|
||||
"SolarpasstroughInfo": "Diese Einstellung aktiviert die direkte Weitergabe der aktuell vom Laderegler gemeldeten Solarleistung an den Wechselrichter um eine unnötige Speicherung zu vermeiden und die Energieverluste zu minimieren.",
|
||||
"InverterId": "Wechselrichter ID",
|
||||
"InverterIdHint": "Wähle den Wechselrichter an dem die Batterie hängt.",
|
||||
|
||||
@ -458,6 +458,9 @@
|
||||
"General": "General",
|
||||
"Enable": "Enable",
|
||||
"EnableSolarPasstrough": "Enable Solar-Passtrough",
|
||||
"BatteryDrainStrategy": "Battery drain strategy",
|
||||
"BatteryDrainWhenFull": "Empty when full",
|
||||
"BatteryDrainAtNight": "Empty at night",
|
||||
"SolarpasstroughInfo": "When the sun is shining, this setting enables the sychronization of the inverter limit with the current solar power of the Victron MPPT charger. This optimizes battery degradation and loses.",
|
||||
"InverterId": "Inverter ID",
|
||||
"InverterIdHint": "Select proper inverter ID where battery is connected to.",
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
export interface PowerLimiterConfig {
|
||||
enabled: boolean;
|
||||
solar_passtrough_enabled: boolean;
|
||||
battery_drain_strategy: number;
|
||||
mqtt_topic_powermeter_1: string;
|
||||
mqtt_topic_powermeter_2: string;
|
||||
mqtt_topic_powermeter_3: string;
|
||||
|
||||
@ -14,6 +14,19 @@
|
||||
:label="$t('powerlimiteradmin.EnableSolarPasstrough')"
|
||||
v-model="powerLimiterConfigList.solar_passtrough_enabled"
|
||||
type="checkbox" wide/>
|
||||
|
||||
<div class="row mb-3" v-show="powerLimiterConfigList.enabled && powerLimiterConfigList.solar_passtrough_enabled">
|
||||
<label for="inputTimezone" class="col-sm-2 col-form-label">
|
||||
{{ $t('powerlimiteradmin.BatteryDrainStrategy') }}:
|
||||
</label>
|
||||
<div class="col-sm-10">
|
||||
<select class="form-select" v-model="powerLimiterConfigList.battery_drain_strategy">
|
||||
<option v-for="batteryDrainStrategy in batteryDrainStrategyList" :key="batteryDrainStrategy.key" :value="batteryDrainStrategy.key">
|
||||
{{ $t(batteryDrainStrategy.value) }}
|
||||
</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="alert alert-secondary" v-show="powerLimiterConfigList.enabled" role="alert" v-html="$t('powerlimiteradmin.SolarpasstroughInfo')"></div>
|
||||
|
||||
@ -256,6 +269,10 @@ export default defineComponent({
|
||||
{ key: 2, value: "CH 2" },
|
||||
{ key: 3, value: "CH 3" },
|
||||
],
|
||||
batteryDrainStrategyList: [
|
||||
{ key: 0, value: "powerlimiteradmin.BatteryDrainWhenFull"},
|
||||
{ key: 1, value: "powerlimiteradmin.BatteryDrainAtNight" },
|
||||
],
|
||||
alertMessage: "",
|
||||
alertType: "info",
|
||||
showAlert: false,
|
||||
|
||||
Binary file not shown.
Loading…
Reference in New Issue
Block a user